--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
LXMF/LXMRouter.py 39e398be65f7c4a46c6d93badb072f335c4580d4 (39e398be) Text, 148.10 KB
Tff7b72import T7ee787os
Tff7b72import T7ee787sys
Tff7b72import T7ee787time
Tff7b72import T7ee787math
Tff7b72import T7ee787random
Tff7b72import T7ee787base64
Tff7b72import T7ee787atexit
Tff7b72import T7ee787signal
Tff7b72import T7ee787threading
Tff7b72from T7ee787collections Tff7b72import Te6edf3deque
Tff7b72import T7ee787RNS
Tff7b72import T7ee787RNST7ee787.T7ee787vendorT7ee787.T7ee787umsgpack Tff7b72as T7ee787msgpack
Tff7b72from T7ee787.T7ee787LXMF Tff7b72import Te6edf3APP_NAME
Tff7b72from T7ee787.T7ee787LXMF Tff7b72import Te6edf3FIELD_TICKET
Tff7b72from T7ee787.T7ee787LXMF Tff7b72import Te6edf3PN_META_NAME
Tff7b72from T7ee787.T7ee787LXMF Tff7b72import Te6edf3pn_announce_data_is_valid
Tff7b72from T7ee787.T7ee787LXMPeer Tff7b72import Te6edf3LXMPeer
Tff7b72from T7ee787.T7ee787LXMessage Tff7b72import Te6edf3LXMessage
Tff7b72from T7ee787.T7ee787Handlers Tff7b72import Te6edf3LXMFDeliveryAnnounceHandler
Tff7b72from T7ee787.T7ee787Handlers Tff7b72import Te6edf3LXMFPropagationAnnounceHandler
Tff7b72import T7ee787LXMFT7ee787.T7ee787LXStamper Tff7b72as T7ee787LXStamper
Tff7b72class T56d364LXMRouterTb4b4b4:
Te6edf3MAX_DELIVERY_ATTEMPTS Tff7b72= T79c0ff5
Te6edf3PROCESSING_INTERVAL Tff7b72= T79c0ff4
Te6edf3DELIVERY_RETRY_WAIT Tff7b72= T79c0ff10
Te6edf3PATH_REQUEST_WAIT Tff7b72= T79c0ff7
Te6edf3MAX_PATHLESS_TRIES Tff7b72= T79c0ff1
Te6edf3LINK_MAX_INACTIVITY Tff7b72= T79c0ff10Tff7b72*T79c0ff60
Te6edf3P_LINK_MAX_INACTIVITY Tff7b72= T79c0ff3Tff7b72*T79c0ff60
Te6edf3MESSAGE_EXPIRY Tff7b72= T79c0ff30Tff7b72*T79c0ff24Tff7b72*T79c0ff60Tff7b72*T79c0ff60
Te6edf3STAMP_COST_EXPIRY Tff7b72= T79c0ff45Tff7b72*T79c0ff24Tff7b72*T79c0ff60Tff7b72*T79c0ff60
Te6edf3NODE_ANNOUNCE_DELAY Tff7b72= T79c0ff20
Te6edf3MAX_PEERS Tff7b72= T79c0ff20
Te6edf3AUTOPEER Tff7b72= Tff7b72True
Te6edf3AUTOPEER_MAXDEPTH Tff7b72= T79c0ff4
Te6edf3FASTEST_N_RANDOM_POOL Tff7b72= T79c0ff2
Te6edf3ROTATION_HEADROOM_PCT Tff7b72= T79c0ff10
Te6edf3ROTATION_AR_MAX Tff7b72= T79c0ff0.5
Te6edf3PEERING_COST Tff7b72= T79c0ff18
Te6edf3MAX_PEERING_COST Tff7b72= T79c0ff26
Te6edf3PROPAGATION_COST_MIN Tff7b72= T79c0ff13
Te6edf3PROPAGATION_COST_FLEX Tff7b72= T79c0ff3
Te6edf3PROPAGATION_COST Tff7b72= T79c0ff16
Te6edf3PROPAGATION_LIMIT Tff7b72= T79c0ff256
Te6edf3SYNC_LIMIT Tff7b72= Te6edf3PROPAGATION_LIMITTff7b72*T79c0ff40
Te6edf3DELIVERY_LIMIT Tff7b72= T79c0ff1000
Te6edf3PR_PATH_TIMEOUT Tff7b72= T79c0ff10
Te6edf3PN_STAMP_THROTTLE Tff7b72= T79c0ff180
Te6edf3PR_IDLE Tff7b72= T79c0ff0x00
Te6edf3PR_PATH_REQUESTED Tff7b72= T79c0ff0x01
Te6edf3PR_LINK_ESTABLISHING Tff7b72= T79c0ff0x02
Te6edf3PR_LINK_ESTABLISHED Tff7b72= T79c0ff0x03
Te6edf3PR_REQUEST_SENT Tff7b72= T79c0ff0x04
Te6edf3PR_RECEIVING Tff7b72= T79c0ff0x05
Te6edf3PR_RESPONSE_RECEIVED Tff7b72= T79c0ff0x06
Te6edf3PR_COMPLETE Tff7b72= T79c0ff0x07
Te6edf3PR_NO_PATH Tff7b72= T79c0ff0xf0
Te6edf3PR_LINK_FAILED Tff7b72= T79c0ff0xf1
Te6edf3PR_TRANSFER_FAILED Tff7b72= T79c0ff0xf2
Te6edf3PR_NO_IDENTITY_RCVD Tff7b72= T79c0ff0xf3
Te6edf3PR_NO_ACCESS Tff7b72= T79c0ff0xf4
Te6edf3PR_FAILED Tff7b72= T79c0ff0xfe
Te6edf3PR_ALL_MESSAGES Tff7b72= T79c0ff0x00
Te6edf3DUPLICATE_SIGNAL Tff7b72= Ta5d6ff"Ta5d6fflxmf_duplicateTa5d6ff"
Te6edf3STATS_GET_PATH Tff7b72= Ta5d6ff"Ta5d6ff/pn/get/statsTa5d6ff"
Te6edf3SYNC_REQUEST_PATH Tff7b72= Ta5d6ff"Ta5d6ff/pn/peer/syncTa5d6ff"
Te6edf3UNPEER_REQUEST_PATH Tff7b72= Ta5d6ff"Ta5d6ff/pn/peer/unpeerTa5d6ff"
T8b949e### Developer-facing API ##############################
T8b949e#######################################################
Tff7b72def Tff7b72__init__Tb4b4b4(Tff7b72selfTb4b4b4, Te6edf3identityTff7b72=Tff7b72NoneTb4b4b4, Te6edf3storagepathTff7b72=Tff7b72NoneTb4b4b4, Te6edf3autopeerTff7b72=Te6edf3AUTOPEERTb4b4b4, Te6edf3autopeer_maxdepthTff7b72=Tff7b72NoneTb4b4b4,
Te6edf3propagation_limitTff7b72=Te6edf3PROPAGATION_LIMITTb4b4b4, Te6edf3delivery_limitTff7b72=Te6edf3DELIVERY_LIMITTb4b4b4, Te6edf3sync_limitTff7b72=Te6edf3SYNC_LIMITTb4b4b4,
Te6edf3enforce_ratchetsTff7b72=Tff7b72FalseTb4b4b4, Te6edf3enforce_stampsTff7b72=Tff7b72FalseTb4b4b4, Te6edf3static_peers Tff7b72= Tb4b4b4[Tb4b4b4]Tb4b4b4, Te6edf3max_peersTff7b72=Tff7b72NoneTb4b4b4,
Te6edf3from_static_onlyTff7b72=Tff7b72FalseTb4b4b4, Te6edf3sync_strategyTff7b72=Te6edf3LXMPeerTff7b72.Td2a8ffSTRATEGY_PERSISTENTTb4b4b4,
Te6edf3propagation_costTff7b72=Te6edf3PROPAGATION_COSTTb4b4b4, Te6edf3propagation_cost_flexibilityTff7b72=Te6edf3PROPAGATION_COST_FLEXTb4b4b4,
Te6edf3peering_costTff7b72=Te6edf3PEERING_COSTTb4b4b4, Te6edf3max_peering_costTff7b72=Te6edf3MAX_PEERING_COSTTb4b4b4, Te6edf3nameTff7b72=Tff7b72NoneTb4b4b4)Tb4b4b4:
Te6edf3randomTff7b72.Td2a8ffseedTb4b4b4(Te6edf3osTff7b72.Td2a8ffurandomTb4b4b4(T79c0ff10Tb4b4b4)Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpending_inbound Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72selfTff7b72.Td2a8ffpending_outbound Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72selfTff7b72.Td2a8fffailed_outbound Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72selfTff7b72.Td2a8ffdirect_links Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72selfTff7b72.Td2a8ffbackchannel_links Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72selfTff7b72.Td2a8ffdelivery_destinations Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72selfTff7b72.Td2a8ffprioritised_list Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72selfTff7b72.Td2a8ffignored_list Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72selfTff7b72.Td2a8ffallowed_list Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72selfTff7b72.Td2a8ffcontrol_allowed_list Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72selfTff7b72.Td2a8ffauth_required Tff7b72= Tff7b72False
Tff7b72selfTff7b72.Td2a8ffretain_synced_on_node Tff7b72= Tff7b72False
Tff7b72selfTff7b72.Td2a8ffdefault_sync_strategy Tff7b72= Te6edf3sync_strategy
Tff7b72selfTff7b72.Td2a8ffprocessing_outbound Tff7b72= Tff7b72False
Tff7b72selfTff7b72.Td2a8ffprocessing_inbound Tff7b72= Tff7b72False
Tff7b72selfTff7b72.Td2a8ffprocessing_count Tff7b72= T79c0ff0
Tff7b72selfTff7b72.Td2a8ffname Tff7b72= Te6edf3name
Tff7b72selfTff7b72.Td2a8ffpropagation_node Tff7b72= Tff7b72False
Tff7b72selfTff7b72.Td2a8ffpropagation_node_start_time Tff7b72= Tff7b72None
Tff7b72if Te6edf3storagepath Tff7b72== Tff7b72NoneTb4b4b4: Tff7b72raise Tf85149ValueErrorTb4b4b4(Ta5d6ff"Ta5d6ffLXMF cannot be initialised without a storage pathTa5d6ff"Tb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffstoragepath Tff7b72= Te6edf3storagepathTff7b72+Ta5d6ff"Ta5d6ff/lxmfTa5d6ff"
Tff7b72selfTff7b72.Td2a8ffratchetpath Tff7b72= Tff7b72selfTff7b72.Td2a8ffstoragepathTff7b72+Ta5d6ff"Ta5d6ff/ratchetsTa5d6ff"
Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_node Tff7b72= Tff7b72None
Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_link Tff7b72= Tff7b72None
Tff7b72if Te6edf3delivery_limit Tff7b72== Tff7b72NoneTb4b4b4: Te6edf3delivery_limit Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffDELIVERY_LIMIT
Tff7b72if Te6edf3propagation_cost Tff7b72< Te6edf3LXMRouterTff7b72.Td2a8ffPROPAGATION_COST_MINTb4b4b4: Te6edf3propagation_cost Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffPROPAGATION_COST_MIN
Tff7b72selfTff7b72.Td2a8ffmessage_storage_limit Tff7b72= Tff7b72None
Tff7b72selfTff7b72.Td2a8ffinformation_storage_limit Tff7b72= Tff7b72None
Tff7b72selfTff7b72.Td2a8ffpropagation_per_transfer_limit Tff7b72= Te6edf3propagation_limit
Tff7b72selfTff7b72.Td2a8ffpropagation_per_sync_limit Tff7b72= Te6edf3sync_limit
Tff7b72selfTff7b72.Td2a8ffdelivery_per_transfer_limit Tff7b72= Te6edf3delivery_limit
Tff7b72selfTff7b72.Td2a8ffpropagation_stamp_cost Tff7b72= Te6edf3propagation_cost
Tff7b72selfTff7b72.Td2a8ffpropagation_stamp_cost_flexibility Tff7b72= Te6edf3propagation_cost_flexibility
Tff7b72selfTff7b72.Td2a8ffpeering_cost Tff7b72= Te6edf3peering_cost
Tff7b72selfTff7b72.Td2a8ffmax_peering_cost Tff7b72= Te6edf3max_peering_cost
Tff7b72selfTff7b72.Td2a8ffenforce_ratchets Tff7b72= Te6edf3enforce_ratchets
Tff7b72selfTff7b72.Td2a8ff_enforce_stamps Tff7b72= Te6edf3enforce_stamps
Tff7b72selfTff7b72.Td2a8ffpending_deferred_stamps Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72selfTff7b72.Td2a8ffthrottled_peers Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72if Te6edf3sync_limit Tff7b72== Tff7b72None Tff7b72or Tff7b72selfTff7b72.Td2a8ffpropagation_per_sync_limit Tff7b72< Tff7b72selfTff7b72.Td2a8ffpropagation_per_transfer_limitTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffpropagation_per_sync_limit Tff7b72= Tff7b72selfTff7b72.Td2a8ffpropagation_per_transfer_limit
Tff7b72selfTff7b72.Td2a8ffwants_download_on_path_available_from Tff7b72= Tff7b72None
Tff7b72selfTff7b72.Td2a8ffwants_download_on_path_available_to Tff7b72= Tff7b72None
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_state Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffPR_IDLE
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_progress Tff7b72= T79c0ff0.0
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_last_result Tff7b72= Tff7b72None
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_last_duplicates Tff7b72= Tff7b72None
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_max_messages Tff7b72= Tff7b72None
Tff7b72selfTff7b72.Td2a8ffprioritise_rotating_unreachable_peers Tff7b72= Tff7b72False
Tff7b72selfTff7b72.Td2a8ffactive_propagation_links Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72selfTff7b72.Td2a8ffvalidated_peer_links Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72selfTff7b72.Td2a8fflocally_delivered_transient_ids Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72selfTff7b72.Td2a8fflocally_processed_transient_ids Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72selfTff7b72.Td2a8ffoutbound_stamp_costs Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72selfTff7b72.Td2a8ffavailable_tickets Tff7b72= Tb4b4b4{Ta5d6ff"Ta5d6ffoutboundTa5d6ff"Tb4b4b4: Tb4b4b4{Tb4b4b4}Tb4b4b4, Ta5d6ff"Ta5d6ffinboundTa5d6ff"Tb4b4b4: Tb4b4b4{Tb4b4b4}Tb4b4b4, Ta5d6ff"Ta5d6fflast_deliveriesTa5d6ff"Tb4b4b4: Tb4b4b4{Tb4b4b4}Tb4b4b4}
Tff7b72selfTff7b72.Td2a8ffcost_file_lock Tff7b72= Te6edf3threadingTff7b72.Td2a8ffLockTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffticket_file_lock Tff7b72= Te6edf3threadingTff7b72.Td2a8ffLockTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffstamp_gen_lock Tff7b72= Te6edf3threadingTff7b72.Td2a8ffLockTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffexit_handler_running Tff7b72= Tff7b72False
Tff7b72if Te6edf3identity Tff7b72== Tff7b72NoneTb4b4b4:
Te6edf3identity Tff7b72= Te6edf3RNSTff7b72.Td2a8ffIdentityTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffidentity Tff7b72= Te6edf3identity
Tff7b72selfTff7b72.Td2a8ffpropagation_destination Tff7b72= Te6edf3RNSTff7b72.Td2a8ffDestinationTb4b4b4(Tff7b72selfTff7b72.Td2a8ffidentityTb4b4b4, Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffINTb4b4b4, Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffSINGLETb4b4b4, Te6edf3APP_NAMETb4b4b4, Ta5d6ff"Ta5d6ffpropagationTa5d6ff"Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_destinationTff7b72.Td2a8ffset_default_app_dataTb4b4b4(Tff7b72selfTff7b72.Td2a8ffget_propagation_node_app_dataTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffcontrol_destination Tff7b72= Tff7b72None
Tff7b72selfTff7b72.Td2a8ffclient_propagation_messages_received Tff7b72= T79c0ff0
Tff7b72selfTff7b72.Td2a8ffclient_propagation_messages_served Tff7b72= T79c0ff0
Tff7b72selfTff7b72.Td2a8ffunpeered_propagation_incoming Tff7b72= T79c0ff0
Tff7b72selfTff7b72.Td2a8ffunpeered_propagation_rx_bytes Tff7b72= T79c0ff0
Tff7b72if Te6edf3autopeer Tff7b72!= Tff7b72NoneTb4b4b4: Tff7b72selfTff7b72.Td2a8ffautopeer Tff7b72= Te6edf3autopeer
Tff7b72elseTb4b4b4: Tff7b72selfTff7b72.Td2a8ffautopeer Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffAUTOPEER
Tff7b72if Te6edf3autopeer_maxdepth Tff7b72!= Tff7b72NoneTb4b4b4: Tff7b72selfTff7b72.Td2a8ffautopeer_maxdepth Tff7b72= Te6edf3autopeer_maxdepth
Tff7b72elseTb4b4b4: Tff7b72selfTff7b72.Td2a8ffautopeer_maxdepth Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffAUTOPEER_MAXDEPTH
Tff7b72if Te6edf3max_peers Tff7b72== Tff7b72NoneTb4b4b4: Tff7b72selfTff7b72.Td2a8ffmax_peers Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffMAX_PEERS
Tff7b72elseTb4b4b4:
Tff7b72if Tffa657typeTb4b4b4(Te6edf3max_peersTb4b4b4) Tff7b72== Tffa657int Tff7b72and Te6edf3max_peers Tff7b72>Tff7b72= T79c0ff0Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffmax_peers Tff7b72= Te6edf3max_peers
Tff7b72elseTb4b4b4: Tff7b72raise Tf85149ValueErrorTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffInvalid value for max_peers: Tffd700{Te6edf3max_peersTffd700}Ta5d6ff"Tb4b4b4)
Tff7b72selfTff7b72.Td2a8fffrom_static_only Tff7b72= Te6edf3from_static_only
Tff7b72if Tffa657typeTb4b4b4(Te6edf3static_peersTb4b4b4) Tff7b72!= Tffa657listTb4b4b4: Tff7b72raise Tf85149ValueErrorTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffInvalid type supplied for static peer list: Tffd700{Tffa657typeTb4b4b4(Te6edf3static_peersTb4b4b4)Tffd700}Ta5d6ff"Tb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72for Te6edf3static_peer Tff7b72in Te6edf3static_peersTb4b4b4:
Tff7b72if Tffa657typeTb4b4b4(Te6edf3static_peerTb4b4b4) Tff7b72!= Tffa657bytesTb4b4b4: Tff7b72raise Tf85149ValueErrorTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffInvalid static peer destination hash: Tffd700{Te6edf3static_peerTffd700}Ta5d6ff"Tb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72if Tffa657lenTb4b4b4(Te6edf3static_peerTb4b4b4) Tff7b72!= Te6edf3RNSTff7b72.Td2a8ffReticulumTff7b72.Td2a8ffTRUNCATED_HASHLENGTHTff7b72/Tff7b72/T79c0ff8Tb4b4b4: Tff7b72raise Tf85149ValueErrorTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffInvalid static peer destination hash: Tffd700{Te6edf3static_peerTffd700}Ta5d6ff"Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffstatic_peers Tff7b72= Te6edf3static_peers
Tff7b72selfTff7b72.Td2a8ffpeers Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72selfTff7b72.Td2a8ffpropagation_entries Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72selfTff7b72.Td2a8ffpeer_distribution_queue Tff7b72= Te6edf3dequeTb4b4b4(Tb4b4b4)
Te6edf3RNSTff7b72.Td2a8ffTransportTff7b72.Td2a8ffregister_announce_handlerTb4b4b4(Te6edf3LXMFDeliveryAnnounceHandlerTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4)
Te6edf3RNSTff7b72.Td2a8ffTransportTff7b72.Td2a8ffregister_announce_handlerTb4b4b4(Te6edf3LXMFPropagationAnnounceHandlerTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ff__delivery_callback Tff7b72= Tff7b72None
Tff7b72tryTb4b4b4:
Tff7b72if Te6edf3osTff7b72.Td2a8ffpathTff7b72.Td2a8ffisfileTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTff7b72+Ta5d6ff"Ta5d6ff/local_deliveriesTa5d6ff"Tb4b4b4)Tb4b4b4:
Te6edf3locally_delivered_file Tff7b72= Tffa657openTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTff7b72+Ta5d6ff"Ta5d6ff/local_deliveriesTa5d6ff"Tb4b4b4, Ta5d6ff"Ta5d6ffrbTa5d6ff"Tb4b4b4)
Te6edf3data Tff7b72= Te6edf3locally_delivered_fileTff7b72.Td2a8ffreadTb4b4b4(Tb4b4b4)
Te6edf3locally_delivered_fileTff7b72.Td2a8ffcloseTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8fflocally_delivered_transient_ids Tff7b72= Te6edf3msgpackTff7b72.Td2a8ffunpackbTb4b4b4(Te6edf3dataTb4b4b4)
Tff7b72if Tff7b72not Tffa657typeTb4b4b4(Tff7b72selfTff7b72.Td2a8fflocally_delivered_transient_idsTb4b4b4) Tff7b72== Tffa657dictTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffInvalid data format for loaded locally delivered transient IDs, recreating...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72selfTff7b72.Td2a8fflocally_delivered_transient_ids Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCould not load locally delivered message ID cache from storage. The contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72selfTff7b72.Td2a8fflocally_delivered_transient_ids Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72tryTb4b4b4:
Tff7b72if Te6edf3osTff7b72.Td2a8ffpathTff7b72.Td2a8ffisfileTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTff7b72+Ta5d6ff"Ta5d6ff/locally_processedTa5d6ff"Tb4b4b4)Tb4b4b4:
Te6edf3locally_processed_file Tff7b72= Tffa657openTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTff7b72+Ta5d6ff"Ta5d6ff/locally_processedTa5d6ff"Tb4b4b4, Ta5d6ff"Ta5d6ffrbTa5d6ff"Tb4b4b4)
Te6edf3data Tff7b72= Te6edf3locally_processed_fileTff7b72.Td2a8ffreadTb4b4b4(Tb4b4b4)
Te6edf3locally_processed_fileTff7b72.Td2a8ffcloseTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8fflocally_processed_transient_ids Tff7b72= Te6edf3msgpackTff7b72.Td2a8ffunpackbTb4b4b4(Te6edf3dataTb4b4b4)
Tff7b72if Tff7b72not Tffa657typeTb4b4b4(Tff7b72selfTff7b72.Td2a8fflocally_processed_transient_idsTb4b4b4) Tff7b72== Tffa657dictTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffInvalid data format for loaded locally processed transient IDs, recreating...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72selfTff7b72.Td2a8fflocally_processed_transient_ids Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCould not load locally processed message ID cache from storage. The contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72selfTff7b72.Td2a8fflocally_processed_transient_ids Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72tryTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffclean_transient_id_cachesTb4b4b4(Tb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCould not clean transient ID caches. The contained exception was : Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72selfTff7b72.Td2a8fflocally_delivered_transient_ids Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72selfTff7b72.Td2a8fflocally_processed_transient_ids Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72tryTb4b4b4:
Tff7b72if Te6edf3osTff7b72.Td2a8ffpathTff7b72.Td2a8ffisfileTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTff7b72+Ta5d6ff"Ta5d6ff/outbound_stamp_costsTa5d6ff"Tb4b4b4)Tb4b4b4:
Tff7b72with Tff7b72selfTff7b72.Td2a8ffcost_file_lockTb4b4b4:
Tff7b72with Tffa657openTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTff7b72+Ta5d6ff"Ta5d6ff/outbound_stamp_costsTa5d6ff"Tb4b4b4, Ta5d6ff"Ta5d6ffrbTa5d6ff"Tb4b4b4) Tff7b72as Te6edf3outbound_stamp_cost_fileTb4b4b4:
Te6edf3data Tff7b72= Te6edf3outbound_stamp_cost_fileTff7b72.Td2a8ffreadTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffoutbound_stamp_costs Tff7b72= Te6edf3msgpackTff7b72.Td2a8ffunpackbTb4b4b4(Te6edf3dataTb4b4b4)
Tff7b72if Tff7b72not Tffa657typeTb4b4b4(Tff7b72selfTff7b72.Td2a8ffoutbound_stamp_costsTb4b4b4) Tff7b72== Tffa657dictTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffInvalid data format for loaded outbound stamp costs, recreating...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffoutbound_stamp_costs Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72selfTff7b72.Td2a8ffclean_outbound_stamp_costsTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffsave_outbound_stamp_costsTb4b4b4(Tb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCould not load outbound stamp costs from storage. The contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72tryTb4b4b4:
Tff7b72if Te6edf3osTff7b72.Td2a8ffpathTff7b72.Td2a8ffisfileTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTff7b72+Ta5d6ff"Ta5d6ff/available_ticketsTa5d6ff"Tb4b4b4)Tb4b4b4:
Tff7b72with Tff7b72selfTff7b72.Td2a8ffticket_file_lockTb4b4b4:
Tff7b72with Tffa657openTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTff7b72+Ta5d6ff"Ta5d6ff/available_ticketsTa5d6ff"Tb4b4b4, Ta5d6ff"Ta5d6ffrbTa5d6ff"Tb4b4b4) Tff7b72as Te6edf3available_tickets_fileTb4b4b4:
Te6edf3data Tff7b72= Te6edf3available_tickets_fileTff7b72.Td2a8ffreadTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffavailable_tickets Tff7b72= Te6edf3msgpackTff7b72.Td2a8ffunpackbTb4b4b4(Te6edf3dataTb4b4b4)
Tff7b72if Tff7b72not Tffa657typeTb4b4b4(Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4) Tff7b72== Tffa657dictTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffInvalid data format for loaded available tickets, recreating...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffavailable_tickets Tff7b72= Tb4b4b4{Ta5d6ff"Ta5d6ffoutboundTa5d6ff"Tb4b4b4: Tb4b4b4{Tb4b4b4}Tb4b4b4, Ta5d6ff"Ta5d6ffinboundTa5d6ff"Tb4b4b4: Tb4b4b4{Tb4b4b4}Tb4b4b4, Ta5d6ff"Ta5d6fflast_deliveriesTa5d6ff"Tb4b4b4: Tb4b4b4{Tb4b4b4}Tb4b4b4}
Tff7b72if Tff7b72not Ta5d6ff"Ta5d6ffoutboundTa5d6ff" Tff7b72in Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffMissing outbound entry in loaded available tickets, recreating...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffoutboundTa5d6ff"Tb4b4b4] Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72if Tff7b72not Ta5d6ff"Ta5d6ffinboundTa5d6ff" Tff7b72in Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffMissing inbound entry in loaded available tickets, recreating...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffinboundTa5d6ff"Tb4b4b4] Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72if Tff7b72not Ta5d6ff"Ta5d6fflast_deliveriesTa5d6ff" Tff7b72in Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffMissing local_deliveries entry in loaded available tickets, recreating...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6fflast_deliveriesTa5d6ff"Tb4b4b4] Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72selfTff7b72.Td2a8ffclean_available_ticketsTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffsave_available_ticketsTb4b4b4(Tb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCould not load outbound stamp costs from storage. The contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Te6edf3atexitTff7b72.Td2a8ffregisterTb4b4b4(Tff7b72selfTff7b72.Td2a8ffexit_handlerTb4b4b4)
Te6edf3signalTff7b72.Td2a8ffsignalTb4b4b4(Te6edf3signalTff7b72.Td2a8ffSIGINTTb4b4b4, Tff7b72selfTff7b72.Td2a8ffsigint_handlerTb4b4b4)
Te6edf3signalTff7b72.Td2a8ffsignalTb4b4b4(Te6edf3signalTff7b72.Td2a8ffSIGTERMTb4b4b4, Tff7b72selfTff7b72.Td2a8ffsigterm_handlerTb4b4b4)
Te6edf3job_thread Tff7b72= Te6edf3threadingTff7b72.Td2a8ffThreadTb4b4b4(Te6edf3targetTff7b72=Tff7b72selfTff7b72.Td2a8ffjobloopTb4b4b4)
Te6edf3job_threadTff7b72.Td2a8ffsetDaemonTb4b4b4(Tff7b72TrueTb4b4b4)
Te6edf3job_threadTff7b72.Td2a8ffstartTb4b4b4(Tb4b4b4)
Tff7b72def Td2a8ffannounceTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3destination_hashTb4b4b4, Te6edf3attached_interfaceTff7b72=Tff7b72NoneTb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffdelivery_destinationsTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffdelivery_destinationsTb4b4b4[Te6edf3destination_hashTb4b4b4]Tff7b72.Td2a8ffannounceTb4b4b4(Te6edf3app_dataTff7b72=Tff7b72selfTff7b72.Td2a8ffget_announce_app_dataTb4b4b4(Te6edf3destination_hashTb4b4b4)Tb4b4b4, Te6edf3attached_interfaceTff7b72=Te6edf3attached_interfaceTb4b4b4)
Tff7b72def Td2a8ffget_propagation_node_announce_metadataTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Te6edf3metadata Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72if Tff7b72selfTff7b72.Td2a8ffnameTb4b4b4: Te6edf3metadataTb4b4b4[Te6edf3PN_META_NAMETb4b4b4] Tff7b72= Tffa657strTb4b4b4(Tff7b72selfTff7b72.Td2a8ffnameTb4b4b4)Tff7b72.Td2a8ffencodeTb4b4b4(Ta5d6ff"Ta5d6ffutf-8Ta5d6ff"Tb4b4b4)
Tff7b72return Te6edf3metadata
Tff7b72def Td2a8ffget_propagation_node_app_dataTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Te6edf3metadata Tff7b72= Tff7b72selfTff7b72.Td2a8ffget_propagation_node_announce_metadataTb4b4b4(Tb4b4b4)
Te6edf3node_state Tff7b72= Tff7b72selfTff7b72.Td2a8ffpropagation_node Tff7b72and Tff7b72not Tff7b72selfTff7b72.Td2a8fffrom_static_only
Te6edf3stamp_cost Tff7b72= Tb4b4b4[Tff7b72selfTff7b72.Td2a8ffpropagation_stamp_costTb4b4b4, Tff7b72selfTff7b72.Td2a8ffpropagation_stamp_cost_flexibilityTb4b4b4, Tff7b72selfTff7b72.Td2a8ffpeering_costTb4b4b4]
Te6edf3announce_data Tff7b72= Tb4b4b4[ Tff7b72FalseTb4b4b4, T8b949e# 0: Legacy LXMF PN support
Tffa657intTb4b4b4(Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)Tb4b4b4)Tb4b4b4, T8b949e# 1: Current node timebase
Te6edf3node_stateTb4b4b4, T8b949e# 2: Boolean flag signalling propagation node state
Tff7b72selfTff7b72.Td2a8ffpropagation_per_transfer_limitTb4b4b4, T8b949e# 3: Per-transfer limit for message propagation in kilobytes
Tff7b72selfTff7b72.Td2a8ffpropagation_per_sync_limitTb4b4b4, T8b949e# 4: Limit for incoming propagation node syncs
Te6edf3stamp_costTb4b4b4, T8b949e# 5: Propagation stamp cost for this node
Te6edf3metadata Tb4b4b4] T8b949e# 6: Node metadata
Tff7b72return Te6edf3msgpackTff7b72.Td2a8ffpackbTb4b4b4(Te6edf3announce_dataTb4b4b4)
Tff7b72def Td2a8ffannounce_propagation_nodeTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72def Td2a8ffdelayed_announceTb4b4b4(Tb4b4b4)Tb4b4b4:
Te6edf3timeTff7b72.Td2a8ffsleepTb4b4b4(Te6edf3LXMRouterTff7b72.Td2a8ffNODE_ANNOUNCE_DELAYTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_destinationTff7b72.Td2a8ffannounceTb4b4b4(Te6edf3app_dataTff7b72=Tff7b72selfTff7b72.Td2a8ffget_propagation_node_app_dataTb4b4b4(Tb4b4b4)Tb4b4b4)
Te6edf3da_thread Tff7b72= Te6edf3threadingTff7b72.Td2a8ffThreadTb4b4b4(Te6edf3targetTff7b72=Te6edf3delayed_announceTb4b4b4)
Te6edf3da_threadTff7b72.Td2a8ffsetDaemonTb4b4b4(Tff7b72TrueTb4b4b4)
Te6edf3da_threadTff7b72.Td2a8ffstartTb4b4b4(Tb4b4b4)
Tff7b72def Td2a8ffregister_delivery_identityTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3identityTb4b4b4, Te6edf3display_name Tff7b72= Tff7b72NoneTb4b4b4, Te6edf3stamp_cost Tff7b72= Tff7b72NoneTb4b4b4)Tb4b4b4:
Tff7b72if Tffa657lenTb4b4b4(Tff7b72selfTff7b72.Td2a8ffdelivery_destinationsTb4b4b4) Tff7b72!= T79c0ff0Tb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCurrently only one delivery identity is supported per LXMF router instanceTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72return Tff7b72None
Tff7b72if Tff7b72not Te6edf3osTff7b72.Td2a8ffpathTff7b72.Td2a8ffisdirTb4b4b4(Tff7b72selfTff7b72.Td2a8ffratchetpathTb4b4b4)Tb4b4b4:
Te6edf3osTff7b72.Td2a8ffmakedirsTb4b4b4(Tff7b72selfTff7b72.Td2a8ffratchetpathTb4b4b4)
Te6edf3delivery_destination Tff7b72= Te6edf3RNSTff7b72.Td2a8ffDestinationTb4b4b4(Te6edf3identityTb4b4b4, Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffINTb4b4b4, Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffSINGLETb4b4b4, Te6edf3APP_NAMETb4b4b4, Ta5d6ff"Ta5d6ffdeliveryTa5d6ff"Tb4b4b4)
Te6edf3delivery_destinationTff7b72.Td2a8ffenable_ratchetsTb4b4b4(Ta5d6fffTa5d6ff"Tffd700{Tff7b72selfTff7b72.Td2a8ffratchetpathTffd700}Ta5d6ff/Tffd700{Te6edf3RNSTff7b72.Td2a8ffhexrepTb4b4b4(Te6edf3delivery_destinationTff7b72.Td2a8ffhashTb4b4b4, Te6edf3delimitTff7b72=Tff7b72FalseTb4b4b4)Tffd700}Ta5d6ff.ratchetsTa5d6ff"Tb4b4b4)
Te6edf3delivery_destinationTff7b72.Td2a8ffset_packet_callbackTb4b4b4(Tff7b72selfTff7b72.Td2a8ffdelivery_packetTb4b4b4)
Te6edf3delivery_destinationTff7b72.Td2a8ffset_link_established_callbackTb4b4b4(Tff7b72selfTff7b72.Td2a8ffdelivery_link_establishedTb4b4b4)
Te6edf3delivery_destinationTff7b72.Td2a8ffdisplay_name Tff7b72= Te6edf3display_name
Tff7b72if Tff7b72selfTff7b72.Td2a8ffenforce_ratchetsTb4b4b4:
Te6edf3delivery_destinationTff7b72.Td2a8ffenforce_ratchetsTb4b4b4(Tb4b4b4)
Tff7b72if Te6edf3display_name Tff7b72!= Tff7b72NoneTb4b4b4:
Tff7b72def Td2a8ffget_app_dataTb4b4b4(Tb4b4b4)Tb4b4b4:
Tff7b72return Tff7b72selfTff7b72.Td2a8ffget_announce_app_dataTb4b4b4(Te6edf3delivery_destinationTff7b72.Td2a8ffhashTb4b4b4)
Te6edf3delivery_destinationTff7b72.Td2a8ffset_default_app_dataTb4b4b4(Te6edf3get_app_dataTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffdelivery_destinationsTb4b4b4[Te6edf3delivery_destinationTff7b72.Td2a8ffhashTb4b4b4] Tff7b72= Te6edf3delivery_destination
Tff7b72selfTff7b72.Td2a8ffset_inbound_stamp_costTb4b4b4(Te6edf3delivery_destinationTff7b72.Td2a8ffhashTb4b4b4, Te6edf3stamp_costTb4b4b4)
Tff7b72return Te6edf3delivery_destination
Tff7b72def Td2a8ffregister_delivery_callbackTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3callbackTb4b4b4)Tb4b4b4:
Tff7b72selfTff7b72.Td2a8ff__delivery_callback Tff7b72= Te6edf3callback
Tff7b72def Td2a8ffset_inbound_stamp_costTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3destination_hashTb4b4b4, Te6edf3stamp_costTb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffdelivery_destinationsTb4b4b4:
Te6edf3delivery_destination Tff7b72= Tff7b72selfTff7b72.Td2a8ffdelivery_destinationsTb4b4b4[Te6edf3destination_hashTb4b4b4]
Tff7b72if Te6edf3stamp_cost Tff7b72== Tff7b72NoneTb4b4b4:
Te6edf3delivery_destinationTff7b72.Td2a8ffstamp_cost Tff7b72= Tff7b72None
Tff7b72return Tff7b72True
Tff7b72elif Tffa657typeTb4b4b4(Te6edf3stamp_costTb4b4b4) Tff7b72== Tffa657intTb4b4b4:
Tff7b72if Te6edf3stamp_cost Tff7b72< T79c0ff1Tb4b4b4:
Te6edf3delivery_destinationTff7b72.Td2a8ffstamp_cost Tff7b72= Tff7b72None
Tff7b72elif Te6edf3stamp_cost Tff7b72< T79c0ff255Tb4b4b4:
Te6edf3delivery_destinationTff7b72.Td2a8ffstamp_cost Tff7b72= Te6edf3stamp_cost
Tff7b72elseTb4b4b4:
Tff7b72return Tff7b72False
Tff7b72return Tff7b72True
Tff7b72return Tff7b72False
Tff7b72def Td2a8ffget_outbound_stamp_costTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3destination_hashTb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffoutbound_stamp_costsTb4b4b4:
Te6edf3stamp_cost Tff7b72= Tff7b72selfTff7b72.Td2a8ffoutbound_stamp_costsTb4b4b4[Te6edf3destination_hashTb4b4b4]Tb4b4b4[T79c0ff1Tb4b4b4]
Tff7b72return Te6edf3stamp_cost
Tff7b72elseTb4b4b4:
Tff7b72return Tff7b72None
Tff7b72def Td2a8ffset_active_propagation_nodeTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3destination_hashTb4b4b4)Tb4b4b4:
Tff7b72selfTff7b72.Td2a8ffset_outbound_propagation_nodeTb4b4b4(Te6edf3destination_hashTb4b4b4)
T8b949e# self.set_inbound_propagation_node(destination_hash)
Tff7b72def Td2a8ffset_outbound_propagation_nodeTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3destination_hashTb4b4b4)Tb4b4b4:
Tff7b72if Tffa657lenTb4b4b4(Te6edf3destination_hashTb4b4b4) Tff7b72!= Te6edf3RNSTff7b72.Td2a8ffIdentityTff7b72.Td2a8ffTRUNCATED_HASHLENGTHTff7b72/Tff7b72/T79c0ff8 Tff7b72or Tffa657typeTb4b4b4(Te6edf3destination_hashTb4b4b4) Tff7b72!= Tffa657bytesTb4b4b4:
Tff7b72raise Tf85149ValueErrorTb4b4b4(Ta5d6ff"Ta5d6ffInvalid destination hash for outbound propagation nodeTa5d6ff"Tb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_node Tff7b72!= Te6edf3destination_hashTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_node Tff7b72= Te6edf3destination_hash
Tff7b72if Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_link Tff7b72!= Tff7b72NoneTb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_linkTff7b72.Td2a8ffdestinationTff7b72.Td2a8ffhash Tff7b72!= Te6edf3destination_hashTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_linkTff7b72.Td2a8ffteardownTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_link Tff7b72= Tff7b72None
Tff7b72def Td2a8ffget_outbound_propagation_nodeTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72return Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_node
Tff7b72def Td2a8ffget_outbound_propagation_costTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Te6edf3target_propagation_cost Tff7b72= Tff7b72None
Te6edf3pn_destination_hash Tff7b72= Tff7b72selfTff7b72.Td2a8ffget_outbound_propagation_nodeTb4b4b4(Tb4b4b4)
Te6edf3pn_app_data Tff7b72= Te6edf3RNSTff7b72.Td2a8ffIdentityTff7b72.Td2a8ffrecall_app_dataTb4b4b4(Te6edf3pn_destination_hashTb4b4b4)
Tff7b72if Te6edf3pn_announce_data_is_validTb4b4b4(Te6edf3pn_app_dataTb4b4b4)Tb4b4b4:
Te6edf3pn_config Tff7b72= Te6edf3msgpackTff7b72.Td2a8ffunpackbTb4b4b4(Te6edf3pn_app_dataTb4b4b4)
Te6edf3target_propagation_cost Tff7b72= Te6edf3pn_configTb4b4b4[T79c0ff5Tb4b4b4]Tb4b4b4[T79c0ff0Tb4b4b4]
Tff7b72if Tff7b72not Te6edf3target_propagation_costTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffCould not retrieve cached propagation node config. Requesting path to propagation node to get target propagation cost...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3RNSTff7b72.Td2a8ffTransportTff7b72.Td2a8ffrequest_pathTb4b4b4(Te6edf3pn_destination_hashTb4b4b4)
Te6edf3timeout Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72+ Te6edf3LXMRouterTff7b72.Td2a8ffPATH_REQUEST_WAIT
Tff7b72while Tff7b72not Te6edf3RNSTff7b72.Td2a8ffIdentityTff7b72.Td2a8ffrecall_app_dataTb4b4b4(Te6edf3pn_destination_hashTb4b4b4) Tff7b72and Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72< Te6edf3timeoutTb4b4b4:
Te6edf3timeTff7b72.Td2a8ffsleepTb4b4b4(T79c0ff0.5Tb4b4b4)
Te6edf3pn_app_data Tff7b72= Te6edf3RNSTff7b72.Td2a8ffIdentityTff7b72.Td2a8ffrecall_app_dataTb4b4b4(Te6edf3pn_destination_hashTb4b4b4)
Tff7b72if Te6edf3pn_announce_data_is_validTb4b4b4(Te6edf3pn_app_dataTb4b4b4)Tb4b4b4:
Te6edf3pn_config Tff7b72= Te6edf3msgpackTff7b72.Td2a8ffunpackbTb4b4b4(Te6edf3pn_app_dataTb4b4b4)
Te6edf3target_propagation_cost Tff7b72= Te6edf3pn_configTb4b4b4[T79c0ff5Tb4b4b4]Tb4b4b4[T79c0ff0Tb4b4b4]
Tff7b72if Tff7b72not Te6edf3target_propagation_costTb4b4b4: Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffPropagation node stamp cost still unavailable after path requestTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72return Te6edf3target_propagation_cost
Tff7b72def Td2a8ffset_inbound_propagation_nodeTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3destination_hashTb4b4b4)Tb4b4b4:
T8b949e# TODO: Implement
Tff7b72raise Tf85149NotImplementedErrorTb4b4b4(Ta5d6ff"Ta5d6ffInbound/outbound propagation node differentiation is currently not implementedTa5d6ff"Tb4b4b4)
Tff7b72def Td2a8ffget_inbound_propagation_nodeTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72return Tff7b72selfTff7b72.Td2a8ffget_outbound_propagation_nodeTb4b4b4(Tb4b4b4)
Tff7b72def Td2a8ffset_retain_node_lxmsTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3retainTb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3retain Tff7b72== Tff7b72TrueTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffretain_synced_on_node Tff7b72= Tff7b72True
Tff7b72elseTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffretain_synced_on_node Tff7b72= Tff7b72False
Tff7b72def Td2a8ffset_authenticationTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3requiredTff7b72=Tff7b72NoneTb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3required Tff7b72!= Tff7b72NoneTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffauth_required Tff7b72= Te6edf3required
Tff7b72def Td2a8ffrequires_authenticationTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72return Tff7b72selfTff7b72.Td2a8ffauth_required
Tff7b72def Td2a8ffallowTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3identity_hashTff7b72=Tff7b72NoneTb4b4b4)Tb4b4b4:
Tff7b72if Tffa657isinstanceTb4b4b4(Te6edf3identity_hashTb4b4b4, Tffa657bytesTb4b4b4) Tff7b72and Tffa657lenTb4b4b4(Te6edf3identity_hashTb4b4b4) Tff7b72== Te6edf3RNSTff7b72.Td2a8ffIdentityTff7b72.Td2a8ffTRUNCATED_HASHLENGTHTff7b72/Tff7b72/T79c0ff8Tb4b4b4:
Tff7b72if Tff7b72not Te6edf3identity_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffallowed_listTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffallowed_listTff7b72.Td2a8ffappendTb4b4b4(Te6edf3identity_hashTb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72raise Tf85149ValueErrorTb4b4b4(Ta5d6ff"Ta5d6ffAllowed identity hash must be Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3RNSTff7b72.Td2a8ffIdentityTff7b72.Td2a8ffTRUNCATED_HASHLENGTHTff7b72/Tff7b72/T79c0ff8Tb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff bytesTa5d6ff"Tb4b4b4)
Tff7b72def Td2a8ffdisallowTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3identity_hashTff7b72=Tff7b72NoneTb4b4b4)Tb4b4b4:
Tff7b72if Tffa657isinstanceTb4b4b4(Te6edf3identity_hashTb4b4b4, Tffa657bytesTb4b4b4) Tff7b72and Tffa657lenTb4b4b4(Te6edf3identity_hashTb4b4b4) Tff7b72== Te6edf3RNSTff7b72.Td2a8ffIdentityTff7b72.Td2a8ffTRUNCATED_HASHLENGTHTff7b72/Tff7b72/T79c0ff8Tb4b4b4:
Tff7b72if Te6edf3identity_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffallowed_listTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffallowed_listTff7b72.Td2a8ffpopTb4b4b4(Te6edf3identity_hashTb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72raise Tf85149ValueErrorTb4b4b4(Ta5d6ff"Ta5d6ffDisallowed identity hash must be Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3RNSTff7b72.Td2a8ffIdentityTff7b72.Td2a8ffTRUNCATED_HASHLENGTHTff7b72/Tff7b72/T79c0ff8Tb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff bytesTa5d6ff"Tb4b4b4)
Tff7b72def Td2a8ffallow_controlTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3identity_hashTff7b72=Tff7b72NoneTb4b4b4)Tb4b4b4:
Tff7b72if Tffa657isinstanceTb4b4b4(Te6edf3identity_hashTb4b4b4, Tffa657bytesTb4b4b4) Tff7b72and Tffa657lenTb4b4b4(Te6edf3identity_hashTb4b4b4) Tff7b72== Te6edf3RNSTff7b72.Td2a8ffIdentityTff7b72.Td2a8ffTRUNCATED_HASHLENGTHTff7b72/Tff7b72/T79c0ff8Tb4b4b4:
Tff7b72if Tff7b72not Te6edf3identity_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffcontrol_allowed_listTb4b4b4: Tff7b72selfTff7b72.Td2a8ffcontrol_allowed_listTff7b72.Td2a8ffappendTb4b4b4(Te6edf3identity_hashTb4b4b4)
Tff7b72elseTb4b4b4: Tff7b72raise Tf85149ValueErrorTb4b4b4(Ta5d6ff"Ta5d6ffAllowed identity hash must be Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3RNSTff7b72.Td2a8ffIdentityTff7b72.Td2a8ffTRUNCATED_HASHLENGTHTff7b72/Tff7b72/T79c0ff8Tb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff bytesTa5d6ff"Tb4b4b4)
Tff7b72def Td2a8ffdisallow_controlTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3identity_hashTff7b72=Tff7b72NoneTb4b4b4)Tb4b4b4:
Tff7b72if Tffa657isinstanceTb4b4b4(Te6edf3identity_hashTb4b4b4, Tffa657bytesTb4b4b4) Tff7b72and Tffa657lenTb4b4b4(Te6edf3identity_hashTb4b4b4) Tff7b72== Te6edf3RNSTff7b72.Td2a8ffIdentityTff7b72.Td2a8ffTRUNCATED_HASHLENGTHTff7b72/Tff7b72/T79c0ff8Tb4b4b4:
Tff7b72if Te6edf3identity_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffcontrol_allowed_listTb4b4b4: Tff7b72selfTff7b72.Td2a8ffcontrol_allowed_listTff7b72.Td2a8ffpopTb4b4b4(Te6edf3identity_hashTb4b4b4)
Tff7b72elseTb4b4b4: Tff7b72raise Tf85149ValueErrorTb4b4b4(Ta5d6ff"Ta5d6ffDisallowed identity hash must be Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3RNSTff7b72.Td2a8ffIdentityTff7b72.Td2a8ffTRUNCATED_HASHLENGTHTff7b72/Tff7b72/T79c0ff8Tb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff bytesTa5d6ff"Tb4b4b4)
Tff7b72def Td2a8ffprioritiseTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3destination_hashTff7b72=Tff7b72NoneTb4b4b4)Tb4b4b4:
Tff7b72if Tffa657isinstanceTb4b4b4(Te6edf3destination_hashTb4b4b4, Tffa657bytesTb4b4b4) Tff7b72and Tffa657lenTb4b4b4(Te6edf3destination_hashTb4b4b4) Tff7b72== Te6edf3RNSTff7b72.Td2a8ffReticulumTff7b72.Td2a8ffTRUNCATED_HASHLENGTHTff7b72/Tff7b72/T79c0ff8Tb4b4b4:
Tff7b72if Tff7b72not Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffprioritised_listTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffprioritised_listTff7b72.Td2a8ffappendTb4b4b4(Te6edf3destination_hashTb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72raise Tf85149ValueErrorTb4b4b4(Ta5d6ff"Ta5d6ffPrioritised destination hash must be Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3RNSTff7b72.Td2a8ffReticulumTff7b72.Td2a8ffTRUNCATED_HASHLENGTHTff7b72/Tff7b72/T79c0ff8Tb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff bytesTa5d6ff"Tb4b4b4)
Tff7b72def Td2a8ffunprioritiseTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3identity_hashTff7b72=Tff7b72NoneTb4b4b4)Tb4b4b4:
Tff7b72if Tffa657isinstanceTb4b4b4(Te6edf3destination_hashTb4b4b4, Tffa657bytesTb4b4b4) Tff7b72and Tffa657lenTb4b4b4(Te6edf3destination_hashTb4b4b4) Tff7b72== Te6edf3RNSTff7b72.Td2a8ffReticulumTff7b72.Td2a8ffTRUNCATED_HASHLENGTHTff7b72/Tff7b72/T79c0ff8Tb4b4b4:
Tff7b72if Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffprioritised_listTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffprioritised_listTff7b72.Td2a8ffpopTb4b4b4(Te6edf3destination_hashTb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72raise Tf85149ValueErrorTb4b4b4(Ta5d6ff"Ta5d6ffPrioritised destination hash must be Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3RNSTff7b72.Td2a8ffReticulumTff7b72.Td2a8ffTRUNCATED_HASHLENGTHTff7b72/Tff7b72/T79c0ff8Tb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff bytesTa5d6ff"Tb4b4b4)
Tff7b72def Td2a8ffrequest_messages_from_propagation_nodeTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3identityTb4b4b4, Te6edf3max_messages Tff7b72= Te6edf3PR_ALL_MESSAGESTb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3max_messages Tff7b72== Tff7b72NoneTb4b4b4:
Te6edf3max_messages Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffPR_ALL_MESSAGES
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_progress Tff7b72= T79c0ff0.0
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_max_messages Tff7b72= Te6edf3max_messages
Tff7b72if Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_node Tff7b72!= Tff7b72NoneTb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_link Tff7b72!= Tff7b72None Tff7b72and Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_linkTff7b72.Td2a8ffstatus Tff7b72== Te6edf3RNSTff7b72.Td2a8ffLinkTff7b72.Td2a8ffACTIVETb4b4b4:
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_state Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffPR_LINK_ESTABLISHED
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffRequesting message list from propagation nodeTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_linkTff7b72.Td2a8ffidentifyTb4b4b4(Te6edf3identityTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_linkTff7b72.Td2a8ffrequestTb4b4b4(
Te6edf3LXMPeerTff7b72.Td2a8ffMESSAGE_GET_PATHTb4b4b4,
Tb4b4b4[Tff7b72NoneTb4b4b4, Tff7b72NoneTb4b4b4]Tb4b4b4, T8b949e# Set both want and have fields to None to get message list
Te6edf3response_callbackTff7b72=Tff7b72selfTff7b72.Td2a8ffmessage_list_responseTb4b4b4,
Te6edf3failed_callbackTff7b72=Tff7b72selfTff7b72.Td2a8ffmessage_get_failed
Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_state Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffPR_REQUEST_SENT
Tff7b72elseTb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_link Tff7b72== Tff7b72NoneTb4b4b4:
Tff7b72if Te6edf3RNSTff7b72.Td2a8ffTransportTff7b72.Td2a8ffhas_pathTb4b4b4(Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_nodeTb4b4b4)Tb4b4b4:
Tff7b72selfTff7b72.Td2a8ffwants_download_on_path_available_from Tff7b72= Tff7b72None
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_state Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffPR_LINK_ESTABLISHING
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffEstablishing link to Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_nodeTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff for message downloadTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3propagation_node_identity Tff7b72= Te6edf3RNSTff7b72.Td2a8ffIdentityTff7b72.Td2a8ffrecallTb4b4b4(Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_nodeTb4b4b4)
Te6edf3propagation_node_destination Tff7b72= Te6edf3RNSTff7b72.Td2a8ffDestinationTb4b4b4(Te6edf3propagation_node_identityTb4b4b4, Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffOUTTb4b4b4, Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffSINGLETb4b4b4, Te6edf3APP_NAMETb4b4b4, Ta5d6ff"Ta5d6ffpropagationTa5d6ff"Tb4b4b4)
Tff7b72def Td2a8ffmsg_request_established_callbackTb4b4b4(Te6edf3linkTb4b4b4)Tb4b4b4:
Tff7b72selfTff7b72.Td2a8ffrequest_messages_from_propagation_nodeTb4b4b4(Te6edf3identityTb4b4b4, Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_max_messagesTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_link Tff7b72= Te6edf3RNSTff7b72.Td2a8ffLinkTb4b4b4(Te6edf3propagation_node_destinationTb4b4b4, Te6edf3established_callbackTff7b72=Te6edf3msg_request_established_callbackTb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffNo path known for message download from propagation node Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_nodeTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff. Requesting path...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3RNSTff7b72.Td2a8ffTransportTff7b72.Td2a8ffrequest_pathTb4b4b4(Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_nodeTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffwants_download_on_path_available_from Tff7b72= Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_node
Tff7b72selfTff7b72.Td2a8ffwants_download_on_path_available_to Tff7b72= Te6edf3identity
Tff7b72selfTff7b72.Td2a8ffwants_download_on_path_available_timeout Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72+ Te6edf3LXMRouterTff7b72.Td2a8ffPR_PATH_TIMEOUT
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_state Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffPR_PATH_REQUESTED
Tff7b72selfTff7b72.Td2a8ffrequest_messages_path_jobTb4b4b4(Tb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffWaiting for propagation node link to become activeTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_EXTREMETb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCannot request LXMF propagation node sync, no default propagation node configuredTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_WARNINGTb4b4b4)
Tff7b72def Td2a8ffcancel_propagation_node_requestsTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_link Tff7b72!= Tff7b72NoneTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_linkTff7b72.Td2a8ffteardownTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_link Tff7b72= Tff7b72None
Tff7b72selfTff7b72.Td2a8ffacknowledge_sync_completionTb4b4b4(Te6edf3reset_stateTff7b72=Tff7b72TrueTb4b4b4)
Tff7b72def Td2a8ffenable_propagationTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72tryTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffmessagepath Tff7b72= Tff7b72selfTff7b72.Td2a8ffstoragepathTff7b72+Ta5d6ff"Ta5d6ff/messagestoreTa5d6ff"
Tff7b72if Tff7b72not Te6edf3osTff7b72.Td2a8ffpathTff7b72.Td2a8ffisdirTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTb4b4b4)Tb4b4b4:
Te6edf3osTff7b72.Td2a8ffmakedirsTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTb4b4b4)
Tff7b72if Tff7b72not Te6edf3osTff7b72.Td2a8ffpathTff7b72.Td2a8ffisdirTb4b4b4(Tff7b72selfTff7b72.Td2a8ffmessagepathTb4b4b4)Tb4b4b4:
Te6edf3osTff7b72.Td2a8ffmakedirsTb4b4b4(Tff7b72selfTff7b72.Td2a8ffmessagepathTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_entries Tff7b72= Tb4b4b4{Tb4b4b4}
Te6edf3st Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)Tb4b4b4; Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffIndexing messagestore...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_NOTICETb4b4b4)
Tff7b72for Te6edf3filename Tff7b72in Te6edf3osTff7b72.Td2a8fflistdirTb4b4b4(Tff7b72selfTff7b72.Td2a8ffmessagepathTb4b4b4)Tb4b4b4:
Te6edf3components Tff7b72= Te6edf3filenameTff7b72.Td2a8ffsplitTb4b4b4(Ta5d6ff"Ta5d6ff_Ta5d6ff"Tb4b4b4)
Tff7b72if Tffa657lenTb4b4b4(Te6edf3componentsTb4b4b4) Tff7b72>Tff7b72= T79c0ff3Tb4b4b4:
Tff7b72if Tffa657floatTb4b4b4(Te6edf3componentsTb4b4b4[T79c0ff1Tb4b4b4]Tb4b4b4) Tff7b72> T79c0ff0Tb4b4b4:
Tff7b72if Tffa657lenTb4b4b4(Te6edf3componentsTb4b4b4[T79c0ff0Tb4b4b4]Tb4b4b4) Tff7b72== Te6edf3RNSTff7b72.Td2a8ffIdentityTff7b72.Td2a8ffHASHLENGTHTff7b72/Tff7b72/T79c0ff8Tff7b72*T79c0ff2Tb4b4b4:
Tff7b72tryTb4b4b4:
Te6edf3transient_id Tff7b72= Tffa657bytesTff7b72.Td2a8fffromhexTb4b4b4(Te6edf3componentsTb4b4b4[T79c0ff0Tb4b4b4]Tb4b4b4)
Te6edf3received Tff7b72= Tffa657floatTb4b4b4(Te6edf3componentsTb4b4b4[T79c0ff1Tb4b4b4]Tb4b4b4)
Te6edf3stamp_value Tff7b72= Tffa657intTb4b4b4(Te6edf3componentsTb4b4b4[T79c0ff2Tb4b4b4]Tb4b4b4)
Te6edf3filepath Tff7b72= Tff7b72selfTff7b72.Td2a8ffmessagepathTff7b72+Ta5d6ff"Ta5d6ff/Ta5d6ff"Tff7b72+Te6edf3filename
Te6edf3msg_size Tff7b72= Te6edf3osTff7b72.Td2a8ffpathTff7b72.Td2a8ffgetsizeTb4b4b4(Te6edf3filepathTb4b4b4)
Te6edf3file Tff7b72= Tffa657openTb4b4b4(Te6edf3filepathTb4b4b4, Ta5d6ff"Ta5d6ffrbTa5d6ff"Tb4b4b4)
Te6edf3destination_hash Tff7b72= Te6edf3fileTff7b72.Td2a8ffreadTb4b4b4(Te6edf3LXMessageTff7b72.Td2a8ffDESTINATION_LENGTHTb4b4b4)
Te6edf3fileTff7b72.Td2a8ffcloseTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTb4b4b4[Te6edf3transient_idTb4b4b4] Tff7b72= Tb4b4b4[
Te6edf3destination_hashTb4b4b4, T8b949e# 0: Destination hash
Te6edf3filepathTb4b4b4, T8b949e# 1: Storage location
Te6edf3receivedTb4b4b4, T8b949e# 2: Receive timestamp
Te6edf3msg_sizeTb4b4b4, T8b949e# 3: Message size
Tb4b4b4[Tb4b4b4]Tb4b4b4, T8b949e# 4: Handled peers
Tb4b4b4[Tb4b4b4]Tb4b4b4, T8b949e# 5: Unhandled peers
Te6edf3stamp_valueTb4b4b4, T8b949e# 6: Stamp value
Tb4b4b4]
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCould not read LXM from message store. The contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Te6edf3et Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)Tb4b4b4; Te6edf3mps Tff7b72= T79c0ff0 Tff7b72if Te6edf3etTff7b72-Te6edf3st Tff7b72== T79c0ff0 Tff7b72else Te6edf3mathTff7b72.Td2a8fffloorTb4b4b4(Tffa657lenTb4b4b4(Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTb4b4b4)Tff7b72/Tb4b4b4(Te6edf3etTff7b72-Te6edf3stTb4b4b4)Tb4b4b4)
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffIndexed Tffd700{Tffa657lenTb4b4b4(Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTb4b4b4)Tffd700}Ta5d6ff messages in Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettytimeTb4b4b4(Te6edf3etTff7b72-Te6edf3stTb4b4b4)Tffd700}Ta5d6ff, Tffd700{Te6edf3mpsTffd700}Ta5d6ff msgs/sTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_NOTICETb4b4b4)
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffRebuilding peer synchronisation states...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_NOTICETb4b4b4)
Te6edf3st Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)
Tff7b72if Te6edf3osTff7b72.Td2a8ffpathTff7b72.Td2a8ffisfileTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTff7b72+Ta5d6ff"Ta5d6ff/peersTa5d6ff"Tb4b4b4)Tb4b4b4:
Te6edf3peers_file Tff7b72= Tffa657openTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTff7b72+Ta5d6ff"Ta5d6ff/peersTa5d6ff"Tb4b4b4, Ta5d6ff"Ta5d6ffrbTa5d6ff"Tb4b4b4)
Te6edf3peers_data Tff7b72= Te6edf3peers_fileTff7b72.Td2a8ffreadTb4b4b4(Tb4b4b4)
Te6edf3peers_fileTff7b72.Td2a8ffcloseTb4b4b4(Tb4b4b4)
Tff7b72if Tffa657lenTb4b4b4(Te6edf3peers_dataTb4b4b4) Tff7b72> T79c0ff0Tb4b4b4:
Te6edf3serialised_peers Tff7b72= Te6edf3msgpackTff7b72.Td2a8ffunpackbTb4b4b4(Te6edf3peers_dataTb4b4b4)
Tff7b72del Te6edf3peers_data
Tff7b72while Tffa657lenTb4b4b4(Te6edf3serialised_peersTb4b4b4) Tff7b72> T79c0ff0Tb4b4b4:
Te6edf3serialised_peer Tff7b72= Te6edf3serialised_peersTff7b72.Td2a8ffpopTb4b4b4(Tb4b4b4)
Te6edf3peer Tff7b72= Te6edf3LXMPeerTff7b72.Td2a8fffrom_bytesTb4b4b4(Te6edf3serialised_peerTb4b4b4, Tff7b72selfTb4b4b4)
Tff7b72del Te6edf3serialised_peer
Tff7b72if Te6edf3peerTff7b72.Td2a8ffdestination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffstatic_peers Tff7b72and Te6edf3peerTff7b72.Td2a8fflast_heard Tff7b72== T79c0ff0Tb4b4b4:
Te6edf3RNSTff7b72.Td2a8ffTransportTff7b72.Td2a8ffrequest_pathTb4b4b4(Te6edf3peerTff7b72.Td2a8ffdestination_hashTb4b4b4)
Tff7b72if Te6edf3peerTff7b72.Td2a8ffidentity Tff7b72!= Tff7b72NoneTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4[Te6edf3peerTff7b72.Td2a8ffdestination_hashTb4b4b4] Tff7b72= Te6edf3peer
Te6edf3lim_str Tff7b72= Ta5d6ff"Ta5d6ff, no transfer limitTa5d6ff"
Tff7b72if Te6edf3peerTff7b72.Td2a8ffpropagation_transfer_limit Tff7b72!= Tff7b72NoneTb4b4b4:
Te6edf3lim_str Tff7b72= Ta5d6ff"Ta5d6ff, Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettysizeTb4b4b4(Te6edf3peerTff7b72.Td2a8ffpropagation_transfer_limitTff7b72*T79c0ff1000Tb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff transfer limitTa5d6ff"
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffRebuilt peer Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3peerTff7b72.Td2a8ffdestination_hashTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff with Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3peerTff7b72.Td2a8ffunhandled_message_countTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff unhandled messagesTa5d6ff"Tff7b72+Te6edf3lim_strTb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffPeer Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3peerTff7b72.Td2a8ffdestination_hashTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff could not be loaded, because its identity could not be recalled. Dropping peer.Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72del Te6edf3peer
Tff7b72del Te6edf3serialised_peers
Tff7b72if Tffa657lenTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstatic_peersTb4b4b4) Tff7b72> T79c0ff0Tb4b4b4:
Tff7b72for Te6edf3static_peer Tff7b72in Tff7b72selfTff7b72.Td2a8ffstatic_peersTb4b4b4:
Tff7b72if Tff7b72not Te6edf3static_peer Tff7b72in Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffActivating static peering with Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3static_peerTb4b4b4)Tffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_NOTICETb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4[Te6edf3static_peerTb4b4b4] Tff7b72= Te6edf3LXMPeerTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3static_peerTb4b4b4, Te6edf3sync_strategyTff7b72=Tff7b72selfTff7b72.Td2a8ffdefault_sync_strategyTb4b4b4)
Tff7b72if Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4[Te6edf3static_peerTb4b4b4]Tff7b72.Td2a8fflast_heard Tff7b72== T79c0ff0Tb4b4b4:
T8b949e# TODO: Allow path request responses through announce handler
T8b949e# momentarily here, so peering config can be updated even if
T8b949e# the static peer is not available to directly send an announce.
Te6edf3RNSTff7b72.Td2a8ffTransportTff7b72.Td2a8ffrequest_pathTb4b4b4(Te6edf3static_peerTb4b4b4)
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffRebuilt synchronisation state for Tffd700{Tffa657lenTb4b4b4(Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4)Tffd700}Ta5d6ff peers in Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettytimeTb4b4b4(Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)Tff7b72-Te6edf3stTb4b4b4)Tffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_NOTICETb4b4b4)
Tff7b72tryTb4b4b4:
Tff7b72if Te6edf3osTff7b72.Td2a8ffpathTff7b72.Td2a8ffisfileTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTff7b72+Ta5d6ff"Ta5d6ff/node_statsTa5d6ff"Tb4b4b4)Tb4b4b4:
Te6edf3node_stats_file Tff7b72= Tffa657openTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTff7b72+Ta5d6ff"Ta5d6ff/node_statsTa5d6ff"Tb4b4b4, Ta5d6ff"Ta5d6ffrbTa5d6ff"Tb4b4b4)
Te6edf3data Tff7b72= Te6edf3node_stats_fileTff7b72.Td2a8ffreadTb4b4b4(Tb4b4b4)
Te6edf3node_stats_fileTff7b72.Td2a8ffcloseTb4b4b4(Tb4b4b4)
Te6edf3node_stats Tff7b72= Te6edf3msgpackTff7b72.Td2a8ffunpackbTb4b4b4(Te6edf3dataTb4b4b4)
Tff7b72if Tff7b72not Tffa657typeTb4b4b4(Te6edf3node_statsTb4b4b4) Tff7b72== Tffa657dictTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffInvalid data format for loaded local node stats, node stats will be resetTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffclient_propagation_messages_received Tff7b72= Te6edf3node_statsTb4b4b4[Ta5d6ff"Ta5d6ffclient_propagation_messages_receivedTa5d6ff"Tb4b4b4]
Tff7b72selfTff7b72.Td2a8ffclient_propagation_messages_served Tff7b72= Te6edf3node_statsTb4b4b4[Ta5d6ff"Ta5d6ffclient_propagation_messages_servedTa5d6ff"Tb4b4b4]
Tff7b72selfTff7b72.Td2a8ffunpeered_propagation_incoming Tff7b72= Te6edf3node_statsTb4b4b4[Ta5d6ff"Ta5d6ffunpeered_propagation_incomingTa5d6ff"Tb4b4b4]
Tff7b72selfTff7b72.Td2a8ffunpeered_propagation_rx_bytes Tff7b72= Te6edf3node_statsTb4b4b4[Ta5d6ff"Ta5d6ffunpeered_propagation_rx_bytesTa5d6ff"Tb4b4b4]
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCould not load local node stats. The contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_node Tff7b72= Tff7b72True
Tff7b72selfTff7b72.Td2a8ffpropagation_node_start_time Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_destinationTff7b72.Td2a8ffset_link_established_callbackTb4b4b4(Tff7b72selfTff7b72.Td2a8ffpropagation_link_establishedTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_destinationTff7b72.Td2a8ffset_packet_callbackTb4b4b4(Tff7b72selfTff7b72.Td2a8ffpropagation_packetTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_destinationTff7b72.Td2a8ffregister_request_handlerTb4b4b4(Te6edf3LXMPeerTff7b72.Td2a8ffOFFER_REQUEST_PATHTb4b4b4, Tff7b72selfTff7b72.Td2a8ffoffer_requestTb4b4b4, Te6edf3allow Tff7b72= Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffALLOW_ALLTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_destinationTff7b72.Td2a8ffregister_request_handlerTb4b4b4(Te6edf3LXMPeerTff7b72.Td2a8ffMESSAGE_GET_PATHTb4b4b4, Tff7b72selfTff7b72.Td2a8ffmessage_get_requestTb4b4b4, Te6edf3allow Tff7b72= Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffALLOW_ALLTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffcontrol_allowed_list Tff7b72= Tb4b4b4[Tff7b72selfTff7b72.Td2a8ffidentityTff7b72.Td2a8ffhashTb4b4b4]
Tff7b72selfTff7b72.Td2a8ffcontrol_destination Tff7b72= Te6edf3RNSTff7b72.Td2a8ffDestinationTb4b4b4(Tff7b72selfTff7b72.Td2a8ffidentityTb4b4b4, Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffINTb4b4b4, Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffSINGLETb4b4b4, Te6edf3APP_NAMETb4b4b4, Ta5d6ff"Ta5d6ffpropagationTa5d6ff"Tb4b4b4, Ta5d6ff"Ta5d6ffcontrolTa5d6ff"Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffcontrol_destinationTff7b72.Td2a8ffregister_request_handlerTb4b4b4(Te6edf3LXMRouterTff7b72.Td2a8ffSTATS_GET_PATHTb4b4b4, Tff7b72selfTff7b72.Td2a8ffstats_get_requestTb4b4b4, Te6edf3allow Tff7b72= Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffALLOW_LISTTb4b4b4, Te6edf3allowed_listTff7b72=Tff7b72selfTff7b72.Td2a8ffcontrol_allowed_listTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffcontrol_destinationTff7b72.Td2a8ffregister_request_handlerTb4b4b4(Te6edf3LXMRouterTff7b72.Td2a8ffSYNC_REQUEST_PATHTb4b4b4, Tff7b72selfTff7b72.Td2a8ffpeer_sync_requestTb4b4b4, Te6edf3allow Tff7b72= Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffALLOW_LISTTb4b4b4, Te6edf3allowed_listTff7b72=Tff7b72selfTff7b72.Td2a8ffcontrol_allowed_listTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffcontrol_destinationTff7b72.Td2a8ffregister_request_handlerTb4b4b4(Te6edf3LXMRouterTff7b72.Td2a8ffUNPEER_REQUEST_PATHTb4b4b4, Tff7b72selfTff7b72.Td2a8ffpeer_unpeer_requestTb4b4b4, Te6edf3allow Tff7b72= Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffALLOW_LISTTb4b4b4, Te6edf3allowed_listTff7b72=Tff7b72selfTff7b72.Td2a8ffcontrol_allowed_listTb4b4b4)
Tff7b72if Tff7b72selfTff7b72.Td2a8ffmessage_storage_limit Tff7b72!= Tff7b72NoneTb4b4b4:
Te6edf3limit_str Tff7b72= Ta5d6ff"Ta5d6ff, limit is Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettysizeTb4b4b4(Tff7b72selfTff7b72.Td2a8ffmessage_storage_limitTb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3limit_str Tff7b72= Ta5d6ff"Ta5d6ff"
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffLXMF Propagation Node message store size is Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettysizeTb4b4b4(Tff7b72selfTff7b72.Td2a8ffmessage_storage_sizeTb4b4b4(Tb4b4b4)Tb4b4b4)Tff7b72+Te6edf3limit_strTb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffannounce_propagation_nodeTb4b4b4(Tb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCould not enable propagation node. The contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72raise Te6edf3e
Te6edf3RNSTff7b72.Td2a8ffpanicTb4b4b4(Tb4b4b4)
Tff7b72def Td2a8ffdisable_propagationTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72selfTff7b72.Td2a8ffpropagation_node Tff7b72= Tff7b72False
Tff7b72selfTff7b72.Td2a8ffannounce_propagation_nodeTb4b4b4(Tb4b4b4)
Tff7b72def Td2a8ffenforce_stampsTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72selfTff7b72.Td2a8ff_enforce_stamps Tff7b72= Tff7b72True
Tff7b72def Td2a8ffignore_stampsTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72selfTff7b72.Td2a8ff_enforce_stamps Tff7b72= Tff7b72False
Tff7b72def Td2a8ffignore_destinationTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3destination_hashTb4b4b4)Tb4b4b4:
Tff7b72if Tff7b72not Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffignored_listTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffignored_listTff7b72.Td2a8ffappendTb4b4b4(Te6edf3destination_hashTb4b4b4)
Tff7b72def Td2a8ffunignore_destinationTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3destination_hashTb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffignored_listTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffignored_listTff7b72.Td2a8ffremoveTb4b4b4(Te6edf3destination_hashTb4b4b4)
Tff7b72def Td2a8ffset_message_storage_limitTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3kilobytes Tff7b72= Tff7b72NoneTb4b4b4, Te6edf3megabytes Tff7b72= Tff7b72NoneTb4b4b4, Te6edf3gigabytes Tff7b72= Tff7b72NoneTb4b4b4)Tb4b4b4:
Te6edf3limit_bytes Tff7b72= T79c0ff0
Tff7b72if Te6edf3kilobytes Tff7b72!= Tff7b72NoneTb4b4b4:
Te6edf3limit_bytes Tff7b72+Tff7b72= Te6edf3kilobytesTff7b72*T79c0ff1000
Tff7b72if Te6edf3megabytes Tff7b72!= Tff7b72NoneTb4b4b4:
Te6edf3limit_bytes Tff7b72+Tff7b72= Te6edf3megabytesTff7b72*T79c0ff1000Tff7b72*T79c0ff1000
Tff7b72if Te6edf3gigabytes Tff7b72!= Tff7b72NoneTb4b4b4:
Te6edf3limit_bytes Tff7b72+Tff7b72= Te6edf3gigabytesTff7b72*T79c0ff1000Tff7b72*T79c0ff1000Tff7b72*T79c0ff1000
Tff7b72if Te6edf3limit_bytes Tff7b72== T79c0ff0Tb4b4b4:
Te6edf3limit_bytes Tff7b72= Tff7b72None
Tff7b72tryTb4b4b4:
Tff7b72if Te6edf3limit_bytes Tff7b72== Tff7b72None Tff7b72or Tffa657intTb4b4b4(Te6edf3limit_bytesTb4b4b4) Tff7b72> T79c0ff0Tb4b4b4:
Tff7b72selfTff7b72.Td2a8ffmessage_storage_limit Tff7b72= Tffa657intTb4b4b4(Te6edf3limit_bytesTb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72raise Tf85149ValueErrorTb4b4b4(Ta5d6ff"Ta5d6ffCannot set LXMF information storage limit to Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3limit_bytesTb4b4b4)Tb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Tff7b72raise Tf85149ValueErrorTb4b4b4(Ta5d6ff"Ta5d6ffCannot set LXMF information storage limit to Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3limit_bytesTb4b4b4)Tb4b4b4)
Tff7b72def Td2a8ffmessage_storage_limitTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72return Tff7b72selfTff7b72.Td2a8ffmessage_storage_limit
Tff7b72def Td2a8ffmessage_storage_sizeTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8ffpropagation_nodeTb4b4b4:
Tff7b72return Tffa657sumTb4b4b4(Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTb4b4b4[Te6edf3fTb4b4b4]Tb4b4b4[T79c0ff3Tb4b4b4] Tff7b72for Te6edf3f Tff7b72in Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72return Tff7b72None
Tff7b72def Td2a8ffset_information_storage_limitTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3kilobytes Tff7b72= Tff7b72NoneTb4b4b4, Te6edf3megabytes Tff7b72= Tff7b72NoneTb4b4b4, Te6edf3gigabytes Tff7b72= Tff7b72NoneTb4b4b4)Tb4b4b4:
Te6edf3limit_bytes Tff7b72= T79c0ff0
Tff7b72if Te6edf3kilobytes Tff7b72!= Tff7b72NoneTb4b4b4: Te6edf3limit_bytes Tff7b72+Tff7b72= Te6edf3kilobytesTff7b72*T79c0ff1000
Tff7b72if Te6edf3megabytes Tff7b72!= Tff7b72NoneTb4b4b4: Te6edf3limit_bytes Tff7b72+Tff7b72= Te6edf3megabytesTff7b72*T79c0ff1000Tff7b72*T79c0ff1000
Tff7b72if Te6edf3gigabytes Tff7b72!= Tff7b72NoneTb4b4b4: Te6edf3limit_bytes Tff7b72+Tff7b72= Te6edf3gigabytesTff7b72*T79c0ff1000Tff7b72*T79c0ff1000Tff7b72*T79c0ff1000
Tff7b72if Te6edf3limit_bytes Tff7b72== T79c0ff0Tb4b4b4: Te6edf3limit_bytes Tff7b72= Tff7b72None
Tff7b72tryTb4b4b4:
Tff7b72if Te6edf3limit_bytes Tff7b72== Tff7b72None Tff7b72or Tffa657intTb4b4b4(Te6edf3limit_bytesTb4b4b4) Tff7b72> T79c0ff0Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffinformation_storage_limit Tff7b72= Tffa657intTb4b4b4(Te6edf3limit_bytesTb4b4b4)
Tff7b72elseTb4b4b4: Tff7b72raise Tf85149ValueErrorTb4b4b4(Ta5d6ff"Ta5d6ffCannot set LXMF information storage limit to Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3limit_bytesTb4b4b4)Tb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4: Tff7b72raise Tf85149ValueErrorTb4b4b4(Ta5d6ff"Ta5d6ffCannot set LXMF information storage limit to Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3limit_bytesTb4b4b4)Tb4b4b4)
Tff7b72def Td2a8ffinformation_storage_limitTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72return Tff7b72selfTff7b72.Td2a8ffinformation_storage_limit
Tff7b72def Td2a8ffinformation_storage_sizeTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72pass
Tff7b72def Td2a8ffdelivery_link_availableTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3destination_hashTb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffdirect_links Tff7b72or Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffbackchannel_linksTb4b4b4: Tff7b72return Tff7b72True
Tff7b72elseTb4b4b4: Tff7b72return Tff7b72False
T8b949e### Propagation Node Control ##########################
T8b949e#######################################################
Tff7b72def Td2a8ffcompile_statsTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72if Tff7b72not Tff7b72selfTff7b72.Td2a8ffpropagation_nodeTb4b4b4: Tff7b72return Tff7b72None
Tff7b72elseTb4b4b4:
Te6edf3peer_stats Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72for Te6edf3peer_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffpeersTff7b72.Td2a8ffcopyTb4b4b4(Tb4b4b4)Tb4b4b4:
Te6edf3peer Tff7b72= Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4[Te6edf3peer_idTb4b4b4]
Te6edf3peer_statsTb4b4b4[Te6edf3peer_idTb4b4b4] Tff7b72= Tb4b4b4{
Ta5d6ff"Ta5d6fftypeTa5d6ff"Tb4b4b4: Ta5d6ff"Ta5d6ffstaticTa5d6ff" Tff7b72if Te6edf3peer_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffstatic_peers Tff7b72else Ta5d6ff"Ta5d6ffdiscoveredTa5d6ff"Tb4b4b4,
Ta5d6ff"Ta5d6ffstateTa5d6ff"Tb4b4b4: Te6edf3peerTff7b72.Td2a8ffstateTb4b4b4,
Ta5d6ff"Ta5d6ffaliveTa5d6ff"Tb4b4b4: Te6edf3peerTff7b72.Td2a8ffaliveTb4b4b4,
Ta5d6ff"Ta5d6ffnameTa5d6ff"Tb4b4b4: Te6edf3peerTff7b72.Td2a8ffnameTb4b4b4,
Ta5d6ff"Ta5d6fflast_heardTa5d6ff"Tb4b4b4: Tffa657intTb4b4b4(Te6edf3peerTff7b72.Td2a8fflast_heardTb4b4b4)Tb4b4b4,
Ta5d6ff"Ta5d6ffnext_sync_attemptTa5d6ff"Tb4b4b4: Te6edf3peerTff7b72.Td2a8ffnext_sync_attemptTb4b4b4,
Ta5d6ff"Ta5d6fflast_sync_attemptTa5d6ff"Tb4b4b4: Te6edf3peerTff7b72.Td2a8fflast_sync_attemptTb4b4b4,
Ta5d6ff"Ta5d6ffsync_backoffTa5d6ff"Tb4b4b4: Te6edf3peerTff7b72.Td2a8ffsync_backoffTb4b4b4,
Ta5d6ff"Ta5d6ffpeering_timebaseTa5d6ff"Tb4b4b4: Te6edf3peerTff7b72.Td2a8ffpeering_timebaseTb4b4b4,
Ta5d6ff"Ta5d6fflerTa5d6ff"Tb4b4b4: Tffa657intTb4b4b4(Te6edf3peerTff7b72.Td2a8fflink_establishment_rateTb4b4b4)Tb4b4b4,
Ta5d6ff"Ta5d6ffstrTa5d6ff"Tb4b4b4: Tffa657intTb4b4b4(Te6edf3peerTff7b72.Td2a8ffsync_transfer_rateTb4b4b4)Tb4b4b4,
Ta5d6ff"Ta5d6fftransfer_limitTa5d6ff"Tb4b4b4: Te6edf3peerTff7b72.Td2a8ffpropagation_transfer_limitTb4b4b4,
Ta5d6ff"Ta5d6ffsync_limitTa5d6ff"Tb4b4b4: Te6edf3peerTff7b72.Td2a8ffpropagation_sync_limitTb4b4b4,
Ta5d6ff"Ta5d6fftarget_stamp_costTa5d6ff"Tb4b4b4: Te6edf3peerTff7b72.Td2a8ffpropagation_stamp_costTb4b4b4,
Ta5d6ff"Ta5d6ffstamp_cost_flexibilityTa5d6ff"Tb4b4b4: Te6edf3peerTff7b72.Td2a8ffpropagation_stamp_cost_flexibilityTb4b4b4,
Ta5d6ff"Ta5d6ffpeering_costTa5d6ff"Tb4b4b4: Te6edf3peerTff7b72.Td2a8ffpeering_costTb4b4b4,
Ta5d6ff"Ta5d6ffpeering_keyTa5d6ff"Tb4b4b4: Te6edf3peerTff7b72.Td2a8ffpeering_key_valueTb4b4b4(Tb4b4b4)Tb4b4b4,
Ta5d6ff"Ta5d6ffnetwork_distanceTa5d6ff"Tb4b4b4: Te6edf3RNSTff7b72.Td2a8ffTransportTff7b72.Td2a8ffhops_toTb4b4b4(Te6edf3peer_idTb4b4b4)Tb4b4b4,
Ta5d6ff"Ta5d6ffrx_bytesTa5d6ff"Tb4b4b4: Te6edf3peerTff7b72.Td2a8ffrx_bytesTb4b4b4,
Ta5d6ff"Ta5d6fftx_bytesTa5d6ff"Tb4b4b4: Te6edf3peerTff7b72.Td2a8fftx_bytesTb4b4b4,
Ta5d6ff"Ta5d6ffacceptance_rateTa5d6ff"Tb4b4b4: Te6edf3peerTff7b72.Td2a8ffacceptance_rateTb4b4b4,
Ta5d6ff"Ta5d6ffmessagesTa5d6ff"Tb4b4b4: Tb4b4b4{
Ta5d6ff"Ta5d6ffofferedTa5d6ff"Tb4b4b4: Te6edf3peerTff7b72.Td2a8ffofferedTb4b4b4,
Ta5d6ff"Ta5d6ffoutgoingTa5d6ff"Tb4b4b4: Te6edf3peerTff7b72.Td2a8ffoutgoingTb4b4b4,
Ta5d6ff"Ta5d6ffincomingTa5d6ff"Tb4b4b4: Te6edf3peerTff7b72.Td2a8ffincomingTb4b4b4,
Ta5d6ff"Ta5d6ffunhandledTa5d6ff"Tb4b4b4: Te6edf3peerTff7b72.Td2a8ffunhandled_message_count
Tb4b4b4}Tb4b4b4,
Tb4b4b4}
Te6edf3node_stats Tff7b72= Tb4b4b4{
Ta5d6ff"Ta5d6ffidentity_hashTa5d6ff"Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffidentityTff7b72.Td2a8ffhashTb4b4b4,
Ta5d6ff"Ta5d6ffdestination_hashTa5d6ff"Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffpropagation_destinationTff7b72.Td2a8ffhashTb4b4b4,
Ta5d6ff"Ta5d6ffuptimeTa5d6ff"Tb4b4b4: Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)Tff7b72-Tff7b72selfTff7b72.Td2a8ffpropagation_node_start_timeTb4b4b4,
Ta5d6ff"Ta5d6ffdelivery_limitTa5d6ff"Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffdelivery_per_transfer_limitTb4b4b4,
Ta5d6ff"Ta5d6ffpropagation_limitTa5d6ff"Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffpropagation_per_transfer_limitTb4b4b4,
Ta5d6ff"Ta5d6ffsync_limitTa5d6ff"Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffpropagation_per_sync_limitTb4b4b4,
Ta5d6ff"Ta5d6fftarget_stamp_costTa5d6ff"Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffpropagation_stamp_costTb4b4b4,
Ta5d6ff"Ta5d6ffstamp_cost_flexibilityTa5d6ff"Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffpropagation_stamp_cost_flexibilityTb4b4b4,
Ta5d6ff"Ta5d6ffpeering_costTa5d6ff"Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffpeering_costTb4b4b4,
Ta5d6ff"Ta5d6ffmax_peering_costTa5d6ff"Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffmax_peering_costTb4b4b4,
Ta5d6ff"Ta5d6ffautopeer_maxdepthTa5d6ff"Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffautopeer_maxdepthTb4b4b4,
Ta5d6ff"Ta5d6fffrom_static_onlyTa5d6ff"Tb4b4b4: Tff7b72selfTff7b72.Td2a8fffrom_static_onlyTb4b4b4,
Ta5d6ff"Ta5d6ffmessagestoreTa5d6ff"Tb4b4b4: Tb4b4b4{
Ta5d6ff"Ta5d6ffcountTa5d6ff"Tb4b4b4: Tffa657lenTb4b4b4(Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTb4b4b4)Tb4b4b4,
Ta5d6ff"Ta5d6ffbytesTa5d6ff"Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffmessage_storage_sizeTb4b4b4(Tb4b4b4)Tb4b4b4,
Ta5d6ff"Ta5d6fflimitTa5d6ff"Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffmessage_storage_limitTb4b4b4,
Tb4b4b4}Tb4b4b4,
Ta5d6ff"Ta5d6ffclientsTa5d6ff" Tb4b4b4: Tb4b4b4{
Ta5d6ff"Ta5d6ffclient_propagation_messages_receivedTa5d6ff"Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffclient_propagation_messages_receivedTb4b4b4,
Ta5d6ff"Ta5d6ffclient_propagation_messages_servedTa5d6ff"Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffclient_propagation_messages_servedTb4b4b4,
Tb4b4b4}Tb4b4b4,
Ta5d6ff"Ta5d6ffunpeered_propagation_incomingTa5d6ff"Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffunpeered_propagation_incomingTb4b4b4,
Ta5d6ff"Ta5d6ffunpeered_propagation_rx_bytesTa5d6ff"Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffunpeered_propagation_rx_bytesTb4b4b4,
Ta5d6ff"Ta5d6ffstatic_peersTa5d6ff"Tb4b4b4: Tffa657lenTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstatic_peersTb4b4b4)Tb4b4b4,
Ta5d6ff"Ta5d6ffdiscovered_peersTa5d6ff"Tb4b4b4: Tffa657lenTb4b4b4(Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4)Tff7b72-Tffa657lenTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstatic_peersTb4b4b4)Tb4b4b4,
Ta5d6ff"Ta5d6fftotal_peersTa5d6ff"Tb4b4b4: Tffa657lenTb4b4b4(Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4)Tb4b4b4,
Ta5d6ff"Ta5d6ffmax_peersTa5d6ff"Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffmax_peersTb4b4b4,
Ta5d6ff"Ta5d6ffpeersTa5d6ff"Tb4b4b4: Te6edf3peer_statsTb4b4b4,
Tb4b4b4}
Tff7b72return Te6edf3node_stats
Tff7b72def Td2a8ffstats_get_requestTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3pathTb4b4b4, Te6edf3dataTb4b4b4, Te6edf3request_idTb4b4b4, Te6edf3remote_identityTb4b4b4, Te6edf3requested_atTb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3remote_identity Tff7b72== Tff7b72NoneTb4b4b4: Tff7b72return Te6edf3LXMPeerTff7b72.Td2a8ffERROR_NO_IDENTITY
Tff7b72elif Te6edf3remote_identityTff7b72.Td2a8ffhash Tff7b72not Tff7b72in Tff7b72selfTff7b72.Td2a8ffcontrol_allowed_listTb4b4b4: Tff7b72return Te6edf3LXMPeerTff7b72.Td2a8ffERROR_NO_ACCESS
Tff7b72elseTb4b4b4: Tff7b72return Tff7b72selfTff7b72.Td2a8ffcompile_statsTb4b4b4(Tb4b4b4)
Tff7b72def Td2a8ffpeer_sync_requestTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3pathTb4b4b4, Te6edf3dataTb4b4b4, Te6edf3request_idTb4b4b4, Te6edf3remote_identityTb4b4b4, Te6edf3requested_atTb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3remote_identity Tff7b72== Tff7b72NoneTb4b4b4: Tff7b72return Te6edf3LXMPeerTff7b72.Td2a8ffERROR_NO_IDENTITY
Tff7b72elif Te6edf3remote_identityTff7b72.Td2a8ffhash Tff7b72not Tff7b72in Tff7b72selfTff7b72.Td2a8ffcontrol_allowed_listTb4b4b4: Tff7b72return Te6edf3LXMPeerTff7b72.Td2a8ffERROR_NO_ACCESS
Tff7b72elseTb4b4b4:
Tff7b72if Tffa657typeTb4b4b4(Te6edf3dataTb4b4b4) Tff7b72!= Tffa657bytesTb4b4b4: Tff7b72return Te6edf3LXMPeerTff7b72.Td2a8ffERROR_INVALID_DATA
Tff7b72elif Tffa657lenTb4b4b4(Te6edf3dataTb4b4b4) Tff7b72!= Te6edf3RNSTff7b72.Td2a8ffIdentityTff7b72.Td2a8ffTRUNCATED_HASHLENGTHTff7b72/Tff7b72/T79c0ff8Tb4b4b4: Tff7b72return Te6edf3LXMPeerTff7b72.Td2a8ffERROR_INVALID_DATA
Tff7b72elseTb4b4b4:
Tff7b72if Tff7b72not Te6edf3data Tff7b72in Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4: Tff7b72return Te6edf3LXMPeerTff7b72.Td2a8ffERROR_NOT_FOUND
Tff7b72elseTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4[Te6edf3dataTb4b4b4]Tff7b72.Td2a8ffsyncTb4b4b4(Tb4b4b4)
Tff7b72return Tff7b72True
Tff7b72def Td2a8ffpeer_unpeer_requestTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3pathTb4b4b4, Te6edf3dataTb4b4b4, Te6edf3request_idTb4b4b4, Te6edf3remote_identityTb4b4b4, Te6edf3requested_atTb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3remote_identity Tff7b72== Tff7b72NoneTb4b4b4: Tff7b72return Te6edf3LXMPeerTff7b72.Td2a8ffERROR_NO_IDENTITY
Tff7b72elif Te6edf3remote_identityTff7b72.Td2a8ffhash Tff7b72not Tff7b72in Tff7b72selfTff7b72.Td2a8ffcontrol_allowed_listTb4b4b4: Tff7b72return Te6edf3LXMPeerTff7b72.Td2a8ffERROR_NO_ACCESS
Tff7b72elseTb4b4b4:
Tff7b72if Tffa657typeTb4b4b4(Te6edf3dataTb4b4b4) Tff7b72!= Tffa657bytesTb4b4b4: Tff7b72return Te6edf3LXMPeerTff7b72.Td2a8ffERROR_INVALID_DATA
Tff7b72elif Tffa657lenTb4b4b4(Te6edf3dataTb4b4b4) Tff7b72!= Te6edf3RNSTff7b72.Td2a8ffIdentityTff7b72.Td2a8ffTRUNCATED_HASHLENGTHTff7b72/Tff7b72/T79c0ff8Tb4b4b4: Tff7b72return Te6edf3LXMPeerTff7b72.Td2a8ffERROR_INVALID_DATA
Tff7b72elseTb4b4b4:
Tff7b72if Tff7b72not Te6edf3data Tff7b72in Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4: Tff7b72return Te6edf3LXMPeerTff7b72.Td2a8ffERROR_NOT_FOUND
Tff7b72elseTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffunpeerTb4b4b4(Te6edf3dataTb4b4b4)
Tff7b72return Tff7b72True
T8b949e### Utility & Maintenance #############################
T8b949e#######################################################
Te6edf3JOB_OUTBOUND_INTERVAL Tff7b72= T79c0ff1
Te6edf3JOB_STAMPS_INTERVAL Tff7b72= T79c0ff1
Te6edf3JOB_LINKS_INTERVAL Tff7b72= T79c0ff1
Te6edf3JOB_TRANSIENT_INTERVAL Tff7b72= T79c0ff60
Te6edf3JOB_STORE_INTERVAL Tff7b72= T79c0ff120
Te6edf3JOB_PEERSYNC_INTERVAL Tff7b72= T79c0ff6
Te6edf3JOB_PEERINGEST_INTERVALTff7b72= Te6edf3JOB_PEERSYNC_INTERVAL
Te6edf3JOB_ROTATE_INTERVAL Tff7b72= T79c0ff56Tff7b72*Te6edf3JOB_PEERINGEST_INTERVAL
Tff7b72def Td2a8ffjobsTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72if Tff7b72not Tff7b72selfTff7b72.Td2a8ffexit_handler_runningTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffprocessing_count Tff7b72+Tff7b72= T79c0ff1
Tff7b72if Tff7b72selfTff7b72.Td2a8ffprocessing_count Tff7b72% Te6edf3LXMRouterTff7b72.Td2a8ffJOB_OUTBOUND_INTERVAL Tff7b72== T79c0ff0Tb4b4b4:
Tff7b72selfTff7b72.Td2a8ffprocess_outboundTb4b4b4(Tb4b4b4)
Tff7b72if Tff7b72selfTff7b72.Td2a8ffprocessing_count Tff7b72% Te6edf3LXMRouterTff7b72.Td2a8ffJOB_STAMPS_INTERVAL Tff7b72== T79c0ff0Tb4b4b4:
Te6edf3threadingTff7b72.Td2a8ffThreadTb4b4b4(Te6edf3targetTff7b72=Tff7b72selfTff7b72.Td2a8ffprocess_deferred_stampsTb4b4b4, Te6edf3daemonTff7b72=Tff7b72TrueTb4b4b4)Tff7b72.Td2a8ffstartTb4b4b4(Tb4b4b4)
Tff7b72if Tff7b72selfTff7b72.Td2a8ffprocessing_count Tff7b72% Te6edf3LXMRouterTff7b72.Td2a8ffJOB_LINKS_INTERVAL Tff7b72== T79c0ff0Tb4b4b4:
Tff7b72selfTff7b72.Td2a8ffclean_linksTb4b4b4(Tb4b4b4)
Tff7b72if Tff7b72selfTff7b72.Td2a8ffprocessing_count Tff7b72% Te6edf3LXMRouterTff7b72.Td2a8ffJOB_TRANSIENT_INTERVAL Tff7b72== T79c0ff0Tb4b4b4:
Tff7b72selfTff7b72.Td2a8ffclean_transient_id_cachesTb4b4b4(Tb4b4b4)
Tff7b72if Tff7b72selfTff7b72.Td2a8ffprocessing_count Tff7b72% Te6edf3LXMRouterTff7b72.Td2a8ffJOB_STORE_INTERVAL Tff7b72== T79c0ff0Tb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8ffpropagation_node Tff7b72== Tff7b72TrueTb4b4b4: Tff7b72selfTff7b72.Td2a8ffclean_message_storeTb4b4b4(Tb4b4b4)
Tff7b72if Tff7b72selfTff7b72.Td2a8ffprocessing_count Tff7b72% Te6edf3LXMRouterTff7b72.Td2a8ffJOB_PEERINGEST_INTERVAL Tff7b72== T79c0ff0Tb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8ffpropagation_node Tff7b72== Tff7b72TrueTb4b4b4: Tff7b72selfTff7b72.Td2a8ffflush_queuesTb4b4b4(Tb4b4b4)
Tff7b72if Tff7b72selfTff7b72.Td2a8ffprocessing_count Tff7b72% Te6edf3LXMRouterTff7b72.Td2a8ffJOB_ROTATE_INTERVAL Tff7b72== T79c0ff0Tb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8ffpropagation_node Tff7b72== Tff7b72TrueTb4b4b4: Tff7b72selfTff7b72.Td2a8ffrotate_peersTb4b4b4(Tb4b4b4)
Tff7b72if Tff7b72selfTff7b72.Td2a8ffprocessing_count Tff7b72% Te6edf3LXMRouterTff7b72.Td2a8ffJOB_PEERSYNC_INTERVAL Tff7b72== T79c0ff0Tb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8ffpropagation_node Tff7b72== Tff7b72TrueTb4b4b4: Tff7b72selfTff7b72.Td2a8ffsync_peersTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffclean_throttled_peersTb4b4b4(Tb4b4b4)
Tff7b72def Td2a8ffjobloopTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72while Tb4b4b4(Tff7b72TrueTb4b4b4)Tb4b4b4:
T8b949e# TODO: Improve this to scheduling, so manual
T8b949e# triggers can delay next run
Tff7b72tryTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffjobsTb4b4b4(Tb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffAn error ocurred while running LXMF Router jobs.Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffThe contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Te6edf3RNSTff7b72.Td2a8fftrace_exceptionTb4b4b4(Te6edf3eTb4b4b4)
Te6edf3timeTff7b72.Td2a8ffsleepTb4b4b4(Te6edf3LXMRouterTff7b72.Td2a8ffPROCESSING_INTERVALTb4b4b4)
Tff7b72def Td2a8ffflush_queuesTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72if Tffa657lenTb4b4b4(Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4) Tff7b72> T79c0ff0Tb4b4b4:
Tff7b72selfTff7b72.Td2a8ffflush_peer_distribution_queueTb4b4b4(Tb4b4b4)
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCalculating peer distribution queue mappings...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)Tb4b4b4; Te6edf3st Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)
Tff7b72for Te6edf3peer_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffpeersTff7b72.Td2a8ffcopyTb4b4b4(Tb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3peer_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4:
Te6edf3peer Tff7b72= Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4[Te6edf3peer_idTb4b4b4]
Tff7b72if Te6edf3peerTff7b72.Td2a8ffqueued_itemsTb4b4b4(Tb4b4b4)Tb4b4b4:
Te6edf3peerTff7b72.Td2a8ffprocess_queuesTb4b4b4(Tb4b4b4)
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffDistribution queue mapping completed in Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettytimeTb4b4b4(Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)Tff7b72-Te6edf3stTb4b4b4)Tffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72def Td2a8ffclean_linksTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Te6edf3closed_links Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72for Te6edf3link_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffdirect_linksTb4b4b4:
Te6edf3link Tff7b72= Tff7b72selfTff7b72.Td2a8ffdirect_linksTb4b4b4[Te6edf3link_hashTb4b4b4]
Te6edf3inactive_time Tff7b72= Te6edf3linkTff7b72.Td2a8ffno_data_forTb4b4b4(Tb4b4b4)
Tff7b72if Te6edf3inactive_time Tff7b72> Te6edf3LXMRouterTff7b72.Td2a8ffLINK_MAX_INACTIVITYTb4b4b4:
Te6edf3linkTff7b72.Td2a8ffteardownTb4b4b4(Tb4b4b4)
Te6edf3closed_linksTff7b72.Td2a8ffappendTb4b4b4(Te6edf3link_hashTb4b4b4)
Tff7b72if Te6edf3linkTff7b72.Td2a8fflink_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffvalidated_peer_linksTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffvalidated_peer_linksTff7b72.Td2a8ffpopTb4b4b4(Te6edf3linkTff7b72.Td2a8fflink_idTb4b4b4)
Tff7b72for Te6edf3link_hash Tff7b72in Te6edf3closed_linksTb4b4b4:
Te6edf3cleaned_link Tff7b72= Tff7b72selfTff7b72.Td2a8ffdirect_linksTff7b72.Td2a8ffpopTb4b4b4(Te6edf3link_hashTb4b4b4)
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCleaned link Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3cleaned_linkTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72tryTb4b4b4:
Te6edf3inactive_links Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72for Te6edf3link Tff7b72in Tff7b72selfTff7b72.Td2a8ffactive_propagation_linksTb4b4b4:
Tff7b72if Te6edf3linkTff7b72.Td2a8ffno_data_forTb4b4b4(Tb4b4b4) Tff7b72> Te6edf3LXMRouterTff7b72.Td2a8ffP_LINK_MAX_INACTIVITYTb4b4b4:
Te6edf3inactive_linksTff7b72.Td2a8ffappendTb4b4b4(Te6edf3linkTb4b4b4)
Tff7b72for Te6edf3link Tff7b72in Te6edf3inactive_linksTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffactive_propagation_linksTff7b72.Td2a8ffremoveTb4b4b4(Te6edf3linkTb4b4b4)
Te6edf3linkTff7b72.Td2a8ffteardownTb4b4b4(Tb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffAn error occurred while cleaning inbound propagation links. The contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72if Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_link Tff7b72!= Tff7b72None Tff7b72and Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_linkTff7b72.Td2a8ffstatus Tff7b72== Te6edf3RNSTff7b72.Td2a8ffLinkTff7b72.Td2a8ffCLOSEDTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_link Tff7b72= Tff7b72None
Tff7b72if Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_state Tff7b72== Te6edf3LXMRouterTff7b72.Td2a8ffPR_COMPLETETb4b4b4:
Tff7b72selfTff7b72.Td2a8ffacknowledge_sync_completionTb4b4b4(Tb4b4b4)
Tff7b72elif Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_state Tff7b72< Te6edf3LXMRouterTff7b72.Td2a8ffPR_LINK_ESTABLISHEDTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffacknowledge_sync_completionTb4b4b4(Te6edf3failure_stateTff7b72=Te6edf3LXMRouterTff7b72.Td2a8ffPR_LINK_FAILEDTb4b4b4)
Tff7b72elif Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_state Tff7b72>Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffPR_LINK_ESTABLISHED Tff7b72and Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_state Tff7b72< Te6edf3LXMRouterTff7b72.Td2a8ffPR_COMPLETETb4b4b4:
Tff7b72selfTff7b72.Td2a8ffacknowledge_sync_completionTb4b4b4(Te6edf3failure_stateTff7b72=Te6edf3LXMRouterTff7b72.Td2a8ffPR_TRANSFER_FAILEDTb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffUnknown propagation transfer state on link cleaning: Tffd700{Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_stateTffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffacknowledge_sync_completionTb4b4b4(Tb4b4b4)
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCleaned outbound propagation linkTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72def Td2a8ffclean_transient_id_cachesTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Te6edf3now Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)
Te6edf3removed_entries Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72for Te6edf3transient_id Tff7b72in Tff7b72selfTff7b72.Td2a8fflocally_delivered_transient_idsTb4b4b4:
Te6edf3timestamp Tff7b72= Tff7b72selfTff7b72.Td2a8fflocally_delivered_transient_idsTb4b4b4[Te6edf3transient_idTb4b4b4]
Tff7b72if Te6edf3now Tff7b72> Te6edf3timestampTff7b72+Te6edf3LXMRouterTff7b72.Td2a8ffMESSAGE_EXPIRYTff7b72*T79c0ff6.0Tb4b4b4:
Te6edf3removed_entriesTff7b72.Td2a8ffappendTb4b4b4(Te6edf3transient_idTb4b4b4)
Tff7b72for Te6edf3transient_id Tff7b72in Te6edf3removed_entriesTb4b4b4:
Tff7b72selfTff7b72.Td2a8fflocally_delivered_transient_idsTff7b72.Td2a8ffpopTb4b4b4(Te6edf3transient_idTb4b4b4)
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCleaned Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3transient_idTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff from local delivery cacheTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3removed_entries Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72for Te6edf3transient_id Tff7b72in Tff7b72selfTff7b72.Td2a8fflocally_processed_transient_idsTb4b4b4:
Te6edf3timestamp Tff7b72= Tff7b72selfTff7b72.Td2a8fflocally_processed_transient_idsTb4b4b4[Te6edf3transient_idTb4b4b4]
Tff7b72if Te6edf3now Tff7b72> Te6edf3timestampTff7b72+Te6edf3LXMRouterTff7b72.Td2a8ffMESSAGE_EXPIRYTff7b72*T79c0ff6.0Tb4b4b4:
Te6edf3removed_entriesTff7b72.Td2a8ffappendTb4b4b4(Te6edf3transient_idTb4b4b4)
Tff7b72for Te6edf3transient_id Tff7b72in Te6edf3removed_entriesTb4b4b4:
Tff7b72selfTff7b72.Td2a8fflocally_processed_transient_idsTff7b72.Td2a8ffpopTb4b4b4(Te6edf3transient_idTb4b4b4)
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCleaned Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3transient_idTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff from locally processed cacheTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72def Td2a8ffupdate_stamp_costTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3destination_hashTb4b4b4, Te6edf3stamp_costTb4b4b4)Tb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffUpdating outbound stamp cost for Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3destination_hashTb4b4b4)Tffd700}Ta5d6ff to Tffd700{Te6edf3stamp_costTffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffoutbound_stamp_costsTb4b4b4[Te6edf3destination_hashTb4b4b4] Tff7b72= Tb4b4b4[Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)Tb4b4b4, Te6edf3stamp_costTb4b4b4]
Tff7b72def Td2a8ffjobTb4b4b4(Tb4b4b4)Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffsave_outbound_stamp_costsTb4b4b4(Tb4b4b4)
Te6edf3threadingTff7b72.Td2a8ffThreadTb4b4b4(Te6edf3targetTff7b72=Tff7b72selfTff7b72.Td2a8ffsave_outbound_stamp_costsTb4b4b4, Te6edf3daemonTff7b72=Tff7b72TrueTb4b4b4)Tff7b72.Td2a8ffstartTb4b4b4(Tb4b4b4)
Tff7b72def Td2a8ffget_announce_app_dataTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3destination_hashTb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffdelivery_destinationsTb4b4b4:
Te6edf3delivery_destination Tff7b72= Tff7b72selfTff7b72.Td2a8ffdelivery_destinationsTb4b4b4[Te6edf3destination_hashTb4b4b4]
Te6edf3display_name Tff7b72= Tff7b72None
Tff7b72if Te6edf3delivery_destinationTff7b72.Td2a8ffdisplay_name Tff7b72!= Tff7b72NoneTb4b4b4:
Te6edf3display_name Tff7b72= Te6edf3delivery_destinationTff7b72.Td2a8ffdisplay_nameTff7b72.Td2a8ffencodeTb4b4b4(Ta5d6ff"Ta5d6ffutf-8Ta5d6ff"Tb4b4b4)
Te6edf3stamp_cost Tff7b72= Tff7b72None
Tff7b72if Te6edf3delivery_destinationTff7b72.Td2a8ffstamp_cost Tff7b72!= Tff7b72None Tff7b72and Tffa657typeTb4b4b4(Te6edf3delivery_destinationTff7b72.Td2a8ffstamp_costTb4b4b4) Tff7b72== Tffa657intTb4b4b4:
Tff7b72if Te6edf3delivery_destinationTff7b72.Td2a8ffstamp_cost Tff7b72> T79c0ff0 Tff7b72and Te6edf3delivery_destinationTff7b72.Td2a8ffstamp_cost Tff7b72< T79c0ff255Tb4b4b4:
Te6edf3stamp_cost Tff7b72= Te6edf3delivery_destinationTff7b72.Td2a8ffstamp_cost
Te6edf3peer_data Tff7b72= Tb4b4b4[Te6edf3display_nameTb4b4b4, Te6edf3stamp_costTb4b4b4]
Tff7b72return Te6edf3msgpackTff7b72.Td2a8ffpackbTb4b4b4(Te6edf3peer_dataTb4b4b4)
Tff7b72def Td2a8ffget_sizeTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3transient_idTb4b4b4)Tb4b4b4:
Te6edf3lxm_size Tff7b72= Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTb4b4b4[Te6edf3transient_idTb4b4b4]Tb4b4b4[T79c0ff3Tb4b4b4]
Tff7b72return Te6edf3lxm_size
Tff7b72def Td2a8ffget_weightTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3transient_idTb4b4b4)Tb4b4b4:
Te6edf3dst_hash Tff7b72= Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTb4b4b4[Te6edf3transient_idTb4b4b4]Tb4b4b4[T79c0ff0Tb4b4b4]
Te6edf3lxm_rcvd Tff7b72= Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTb4b4b4[Te6edf3transient_idTb4b4b4]Tb4b4b4[T79c0ff2Tb4b4b4]
Te6edf3lxm_size Tff7b72= Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTb4b4b4[Te6edf3transient_idTb4b4b4]Tb4b4b4[T79c0ff3Tb4b4b4]
Te6edf3now Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)
Te6edf3age_weight Tff7b72= Tffa657maxTb4b4b4(T79c0ff1Tb4b4b4, Tb4b4b4(Te6edf3now Tff7b72- Te6edf3lxm_rcvdTb4b4b4)Tff7b72/T79c0ff60Tff7b72/T79c0ff60Tff7b72/T79c0ff24Tff7b72/T79c0ff4Tb4b4b4)
Tff7b72if Te6edf3dst_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffprioritised_listTb4b4b4: Te6edf3priority_weight Tff7b72= T79c0ff0.1
Tff7b72elseTb4b4b4: Te6edf3priority_weight Tff7b72= T79c0ff1.0
Tff7b72return Te6edf3priority_weight Tff7b72* Te6edf3age_weight Tff7b72* Te6edf3lxm_size
Tff7b72def Td2a8ffget_stamp_valueTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3transient_idTb4b4b4)Tb4b4b4:
Tff7b72if Tff7b72not Te6edf3transient_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTb4b4b4: Tff7b72return Tff7b72None
Tff7b72elseTb4b4b4: Tff7b72return Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTb4b4b4[Te6edf3transient_idTb4b4b4]Tb4b4b4[T79c0ff6Tb4b4b4]
Tff7b72def Td2a8ffgenerate_ticketTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3destination_hashTb4b4b4, Te6edf3expiryTff7b72=Te6edf3LXMessageTff7b72.Td2a8ffTICKET_EXPIRYTb4b4b4)Tb4b4b4:
Te6edf3now Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)
Te6edf3ticket Tff7b72= Tff7b72None
Tff7b72if Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6fflast_deliveriesTa5d6ff"Tb4b4b4]Tb4b4b4:
Te6edf3last_delivery Tff7b72= Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6fflast_deliveriesTa5d6ff"Tb4b4b4]Tb4b4b4[Te6edf3destination_hashTb4b4b4]
Te6edf3elapsed Tff7b72= Te6edf3now Tff7b72- Te6edf3last_delivery
Tff7b72if Te6edf3elapsed Tff7b72< Te6edf3LXMessageTff7b72.Td2a8ffTICKET_INTERVALTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffA ticket for Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3destination_hashTb4b4b4)Tffd700}Ta5d6ff was already delivered Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettytimeTb4b4b4(Te6edf3elapsedTb4b4b4)Tffd700}Ta5d6ff ago, not including another ticket yetTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72return Tff7b72None
Tff7b72if Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffinboundTa5d6ff"Tb4b4b4]Tb4b4b4:
Tff7b72for Te6edf3ticket Tff7b72in Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffinboundTa5d6ff"Tb4b4b4]Tb4b4b4[Te6edf3destination_hashTb4b4b4]Tb4b4b4:
Te6edf3ticket_entry Tff7b72= Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffinboundTa5d6ff"Tb4b4b4]Tb4b4b4[Te6edf3destination_hashTb4b4b4]Tb4b4b4[Te6edf3ticketTb4b4b4]
Te6edf3expires Tff7b72= Te6edf3ticket_entryTb4b4b4[T79c0ff0Tb4b4b4]Tb4b4b4; Te6edf3validity_left Tff7b72= Te6edf3expires Tff7b72- Te6edf3now
Tff7b72if Te6edf3validity_left Tff7b72> Te6edf3LXMessageTff7b72.Td2a8ffTICKET_RENEWTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffFound generated ticket for Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3destination_hashTb4b4b4)Tffd700}Ta5d6ff with Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettytimeTb4b4b4(Te6edf3validity_leftTb4b4b4)Tffd700}Ta5d6ff of validity left, re-using this oneTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72return Tb4b4b4[Te6edf3expiresTb4b4b4, Te6edf3ticketTb4b4b4]
Tff7b72elseTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffinboundTa5d6ff"Tb4b4b4]Tb4b4b4[Te6edf3destination_hashTb4b4b4] Tff7b72= Tb4b4b4{Tb4b4b4}
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffNo generated tickets for Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3destination_hashTb4b4b4)Tffd700}Ta5d6ff with enough validity found, generating a new oneTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3expires Tff7b72= Te6edf3nowTff7b72+Te6edf3expiry
Te6edf3ticket Tff7b72= Te6edf3osTff7b72.Td2a8ffurandomTb4b4b4(Te6edf3LXMessageTff7b72.Td2a8ffTICKET_LENGTHTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffinboundTa5d6ff"Tb4b4b4]Tb4b4b4[Te6edf3destination_hashTb4b4b4]Tb4b4b4[Te6edf3ticketTb4b4b4] Tff7b72= Tb4b4b4[Te6edf3expiresTb4b4b4]
Tff7b72selfTff7b72.Td2a8ffsave_available_ticketsTb4b4b4(Tb4b4b4)
Tff7b72return Tb4b4b4[Te6edf3expiresTb4b4b4, Te6edf3ticketTb4b4b4]
Tff7b72def Td2a8ffremember_ticketTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3destination_hashTb4b4b4, Te6edf3ticket_entryTb4b4b4)Tb4b4b4:
Te6edf3expires Tff7b72= Te6edf3ticket_entryTb4b4b4[T79c0ff0Tb4b4b4]Tff7b72-Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffRemembering ticket for Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3destination_hashTb4b4b4)Tffd700}Ta5d6ff, expires in Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettytimeTb4b4b4(Te6edf3expiresTb4b4b4)Tffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffoutboundTa5d6ff"Tb4b4b4]Tb4b4b4[Te6edf3destination_hashTb4b4b4] Tff7b72= Tb4b4b4[Te6edf3ticket_entryTb4b4b4[T79c0ff0Tb4b4b4]Tb4b4b4, Te6edf3ticket_entryTb4b4b4[T79c0ff1Tb4b4b4]Tb4b4b4]
Tff7b72def Td2a8ffget_outbound_ticketTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3destination_hashTb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffoutboundTa5d6ff"Tb4b4b4]Tb4b4b4:
Te6edf3entry Tff7b72= Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffoutboundTa5d6ff"Tb4b4b4]Tb4b4b4[Te6edf3destination_hashTb4b4b4]
Tff7b72if Te6edf3entryTb4b4b4[T79c0ff0Tb4b4b4] Tff7b72> Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)Tb4b4b4:
Tff7b72return Te6edf3entryTb4b4b4[T79c0ff1Tb4b4b4]
Tff7b72return Tff7b72None
Tff7b72def Td2a8ffget_outbound_ticket_expiryTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3destination_hashTb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffoutboundTa5d6ff"Tb4b4b4]Tb4b4b4:
Te6edf3entry Tff7b72= Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffoutboundTa5d6ff"Tb4b4b4]Tb4b4b4[Te6edf3destination_hashTb4b4b4]
Tff7b72if Te6edf3entryTb4b4b4[T79c0ff0Tb4b4b4] Tff7b72> Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)Tb4b4b4:
Tff7b72return Te6edf3entryTb4b4b4[T79c0ff0Tb4b4b4]
Tff7b72return Tff7b72None
Tff7b72def Td2a8ffget_inbound_ticketsTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3destination_hashTb4b4b4)Tb4b4b4:
Te6edf3now Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)
Te6edf3available_tickets Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72if Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffinboundTa5d6ff"Tb4b4b4]Tb4b4b4:
Tff7b72for Te6edf3inbound_ticket Tff7b72in Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffinboundTa5d6ff"Tb4b4b4]Tb4b4b4[Te6edf3destination_hashTb4b4b4]Tb4b4b4:
Tff7b72if Te6edf3now Tff7b72< Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffinboundTa5d6ff"Tb4b4b4]Tb4b4b4[Te6edf3destination_hashTb4b4b4]Tb4b4b4[Te6edf3inbound_ticketTb4b4b4]Tb4b4b4[T79c0ff0Tb4b4b4]Tb4b4b4:
Te6edf3available_ticketsTff7b72.Td2a8ffappendTb4b4b4(Te6edf3inbound_ticketTb4b4b4)
Tff7b72if Tffa657lenTb4b4b4(Te6edf3available_ticketsTb4b4b4) Tff7b72== T79c0ff0Tb4b4b4:
Tff7b72return Tff7b72None
Tff7b72elseTb4b4b4:
Tff7b72return Te6edf3available_tickets
Tff7b72def Td2a8ffclean_throttled_peersTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Te6edf3expired_entries Tff7b72= Tb4b4b4[Tb4b4b4]
Te6edf3now Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)
Tff7b72for Te6edf3peer_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffthrottled_peersTb4b4b4:
Tff7b72if Te6edf3now Tff7b72> Tff7b72selfTff7b72.Td2a8ffthrottled_peersTb4b4b4[Te6edf3peer_hashTb4b4b4]Tb4b4b4: Te6edf3expired_entriesTff7b72.Td2a8ffappendTb4b4b4(Te6edf3peer_hashTb4b4b4)
Tff7b72for Te6edf3peer_hash Tff7b72in Te6edf3expired_entriesTb4b4b4: Tff7b72selfTff7b72.Td2a8ffthrottled_peersTff7b72.Td2a8ffpopTb4b4b4(Te6edf3peer_hashTb4b4b4)
Tff7b72def Td2a8ffclean_message_storeTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCleaning message storeTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_VERBOSETb4b4b4)
T8b949e# Check and remove expired messages
Te6edf3now Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)
Te6edf3removed_entries Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72for Te6edf3transient_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTff7b72.Td2a8ffcopyTb4b4b4(Tb4b4b4)Tb4b4b4:
Te6edf3entry Tff7b72= Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTb4b4b4[Te6edf3transient_idTb4b4b4]
Te6edf3filepath Tff7b72= Te6edf3entryTb4b4b4[T79c0ff1Tb4b4b4]
Te6edf3stamp_value Tff7b72= Te6edf3entryTb4b4b4[T79c0ff6Tb4b4b4]
Te6edf3filename Tff7b72= Te6edf3osTff7b72.Td2a8ffpathTff7b72.Td2a8ffsplitTb4b4b4(Te6edf3filepathTb4b4b4)Tb4b4b4[Tff7b72-T79c0ff1Tb4b4b4]
Te6edf3components Tff7b72= Te6edf3filenameTff7b72.Td2a8ffsplitTb4b4b4(Ta5d6ff"Ta5d6ff_Ta5d6ff"Tb4b4b4)
Tff7b72if Tffa657lenTb4b4b4(Te6edf3componentsTb4b4b4) Tff7b72== T79c0ff3 Tff7b72and Tffa657floatTb4b4b4(Te6edf3componentsTb4b4b4[T79c0ff1Tb4b4b4]Tb4b4b4) Tff7b72> T79c0ff0 Tff7b72and Tffa657lenTb4b4b4(Te6edf3osTff7b72.Td2a8ffpathTff7b72.Td2a8ffsplitTb4b4b4(Te6edf3componentsTb4b4b4[T79c0ff0Tb4b4b4]Tb4b4b4)Tb4b4b4[T79c0ff1Tb4b4b4]Tb4b4b4) Tff7b72== Tb4b4b4(Te6edf3RNSTff7b72.Td2a8ffIdentityTff7b72.Td2a8ffHASHLENGTHTff7b72/Tff7b72/T79c0ff8Tb4b4b4)Tff7b72*T79c0ff2 Tff7b72and Tffa657intTb4b4b4(Te6edf3componentsTb4b4b4[T79c0ff2Tb4b4b4]Tb4b4b4) Tff7b72== Te6edf3stamp_valueTb4b4b4:
Te6edf3timestamp Tff7b72= Tffa657floatTb4b4b4(Te6edf3componentsTb4b4b4[T79c0ff1Tb4b4b4]Tb4b4b4)
Tff7b72if Te6edf3now Tff7b72> Te6edf3timestampTff7b72+Te6edf3LXMRouterTff7b72.Td2a8ffMESSAGE_EXPIRYTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffPurging message Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3transient_idTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff due to expiryTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_EXTREMETb4b4b4)
Te6edf3removed_entriesTb4b4b4[Te6edf3transient_idTb4b4b4] Tff7b72= Te6edf3filepath
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffPurging message Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3transient_idTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff due to invalid file pathTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_WARNINGTb4b4b4)
Te6edf3removed_entriesTb4b4b4[Te6edf3transient_idTb4b4b4] Tff7b72= Te6edf3filepath
Te6edf3removed_count Tff7b72= T79c0ff0
Tff7b72for Te6edf3transient_id Tff7b72in Te6edf3removed_entriesTb4b4b4:
Tff7b72tryTb4b4b4:
Te6edf3filepath Tff7b72= Te6edf3removed_entriesTb4b4b4[Te6edf3transient_idTb4b4b4]
Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTff7b72.Td2a8ffpopTb4b4b4(Te6edf3transient_idTb4b4b4)
Tff7b72if Te6edf3osTff7b72.Td2a8ffpathTff7b72.Td2a8ffisfileTb4b4b4(Te6edf3filepathTb4b4b4)Tb4b4b4:
Te6edf3osTff7b72.Td2a8ffunlinkTb4b4b4(Te6edf3filepathTb4b4b4)
Te6edf3removed_count Tff7b72+Tff7b72= T79c0ff1
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCould not remove Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3transient_idTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff from message store. The contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72if Te6edf3removed_count Tff7b72> T79c0ff0Tb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCleaned Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3removed_countTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff entries from the message storeTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_VERBOSETb4b4b4)
T8b949e# Check size of message store and cull if needed
Tff7b72tryTb4b4b4:
Te6edf3message_storage_size Tff7b72= Tff7b72selfTff7b72.Td2a8ffmessage_storage_sizeTb4b4b4(Tb4b4b4)
Tff7b72if Te6edf3message_storage_size Tff7b72!= Tff7b72NoneTb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8ffmessage_storage_limit Tff7b72!= Tff7b72None Tff7b72and Te6edf3message_storage_size Tff7b72> Tff7b72selfTff7b72.Td2a8ffmessage_storage_limitTb4b4b4:
T8b949e# Clean the message storage according to priorities
Te6edf3bytes_needed Tff7b72= Te6edf3message_storage_size Tff7b72- Tff7b72selfTff7b72.Td2a8ffmessage_storage_limit
Te6edf3bytes_cleaned Tff7b72= T79c0ff0
Te6edf3weighted_entries Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72for Te6edf3transient_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTff7b72.Td2a8ffcopyTb4b4b4(Tb4b4b4)Tb4b4b4:
Te6edf3weighted_entriesTff7b72.Td2a8ffappendTb4b4b4(Tb4b4b4[
Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTb4b4b4[Te6edf3transient_idTb4b4b4]Tb4b4b4,
Tff7b72selfTff7b72.Td2a8ffget_weightTb4b4b4(Te6edf3transient_idTb4b4b4)Tb4b4b4,
Te6edf3transient_id
Tb4b4b4]Tb4b4b4)
Te6edf3weighted_entriesTff7b72.Td2a8ffsortTb4b4b4(Te6edf3keyTff7b72=Tff7b72lambda Te6edf3weTb4b4b4: Te6edf3weTb4b4b4[T79c0ff1Tb4b4b4]Tb4b4b4, Te6edf3reverseTff7b72=Tff7b72TrueTb4b4b4)
Te6edf3i Tff7b72= T79c0ff0
Tff7b72while Te6edf3i Tff7b72< Tffa657lenTb4b4b4(Te6edf3weighted_entriesTb4b4b4) Tff7b72and Te6edf3bytes_cleaned Tff7b72< Te6edf3bytes_neededTb4b4b4:
Tff7b72tryTb4b4b4:
Te6edf3w Tff7b72= Te6edf3weighted_entriesTb4b4b4[Te6edf3iTb4b4b4]
Te6edf3entry Tff7b72= Te6edf3wTb4b4b4[T79c0ff0Tb4b4b4]
Te6edf3transient_id Tff7b72= Te6edf3wTb4b4b4[T79c0ff2Tb4b4b4]
Te6edf3filepath Tff7b72= Te6edf3entryTb4b4b4[T79c0ff1Tb4b4b4]
Tff7b72if Te6edf3osTff7b72.Td2a8ffpathTff7b72.Td2a8ffisfileTb4b4b4(Te6edf3filepathTb4b4b4)Tb4b4b4:
Te6edf3osTff7b72.Td2a8ffunlinkTb4b4b4(Te6edf3filepathTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTff7b72.Td2a8ffpopTb4b4b4(Te6edf3transient_idTb4b4b4)
Te6edf3bytes_cleaned Tff7b72+Tff7b72= Te6edf3entryTb4b4b4[T79c0ff3Tb4b4b4]
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffRemoved Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3transient_idTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff with weight Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3wTb4b4b4[T79c0ff1Tb4b4b4]Tb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff to clear up Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettysizeTb4b4b4(Te6edf3entryTb4b4b4[T79c0ff3Tb4b4b4]Tb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff, now cleaned Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettysizeTb4b4b4(Te6edf3bytes_cleanedTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff out of Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettysizeTb4b4b4(Te6edf3bytes_neededTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff neededTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_EXTREMETb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffError while cleaning LXMF message from message store. The contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72finallyTb4b4b4:
Te6edf3i Tff7b72+Tff7b72= T79c0ff1
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffLXMF message store size is now Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettysizeTb4b4b4(Tff7b72selfTff7b72.Td2a8ffmessage_storage_sizeTb4b4b4(Tb4b4b4)Tb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff for Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Tffa657lenTb4b4b4(Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTb4b4b4)Tb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff itemsTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_EXTREMETb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCould not clean the LXMF message store. The contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72def Td2a8ffsave_locally_delivered_transient_idsTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72tryTb4b4b4:
Tff7b72if Tffa657lenTb4b4b4(Tff7b72selfTff7b72.Td2a8fflocally_delivered_transient_idsTb4b4b4) Tff7b72> T79c0ff0Tb4b4b4:
Tff7b72if Tff7b72not Te6edf3osTff7b72.Td2a8ffpathTff7b72.Td2a8ffisdirTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTb4b4b4)Tb4b4b4:
Te6edf3osTff7b72.Td2a8ffmakedirsTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTb4b4b4)
Tff7b72with Tffa657openTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTff7b72+Ta5d6ff"Ta5d6ff/local_deliveriesTa5d6ff"Tb4b4b4, Ta5d6ff"Ta5d6ffwbTa5d6ff"Tb4b4b4) Tff7b72as Te6edf3locally_delivered_fileTb4b4b4:
Te6edf3locally_delivered_fileTff7b72.Td2a8ffwriteTb4b4b4(Te6edf3msgpackTff7b72.Td2a8ffpackbTb4b4b4(Tff7b72selfTff7b72.Td2a8fflocally_delivered_transient_idsTb4b4b4)Tb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCould not save locally delivered message ID cache to storage. The contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72def Td2a8ffsave_locally_processed_transient_idsTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72tryTb4b4b4:
Tff7b72if Tffa657lenTb4b4b4(Tff7b72selfTff7b72.Td2a8fflocally_processed_transient_idsTb4b4b4) Tff7b72> T79c0ff0Tb4b4b4:
Tff7b72if Tff7b72not Te6edf3osTff7b72.Td2a8ffpathTff7b72.Td2a8ffisdirTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTb4b4b4)Tb4b4b4:
Te6edf3osTff7b72.Td2a8ffmakedirsTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTb4b4b4)
Tff7b72with Tffa657openTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTff7b72+Ta5d6ff"Ta5d6ff/locally_processedTa5d6ff"Tb4b4b4, Ta5d6ff"Ta5d6ffwbTa5d6ff"Tb4b4b4) Tff7b72as Te6edf3locally_processed_fileTb4b4b4:
Te6edf3locally_processed_fileTff7b72.Td2a8ffwriteTb4b4b4(Te6edf3msgpackTff7b72.Td2a8ffpackbTb4b4b4(Tff7b72selfTff7b72.Td2a8fflocally_processed_transient_idsTb4b4b4)Tb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCould not save locally processed transient ID cache to storage. The contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72def Td2a8ffsave_node_statsTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72tryTb4b4b4:
Tff7b72if Tff7b72not Te6edf3osTff7b72.Td2a8ffpathTff7b72.Td2a8ffisdirTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTb4b4b4)Tb4b4b4:
Te6edf3osTff7b72.Td2a8ffmakedirsTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTb4b4b4)
Tff7b72with Tffa657openTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTff7b72+Ta5d6ff"Ta5d6ff/node_statsTa5d6ff"Tb4b4b4, Ta5d6ff"Ta5d6ffwbTa5d6ff"Tb4b4b4) Tff7b72as Te6edf3stats_fileTb4b4b4:
Te6edf3node_stats Tff7b72= Tb4b4b4{
Ta5d6ff"Ta5d6ffclient_propagation_messages_receivedTa5d6ff"Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffclient_propagation_messages_receivedTb4b4b4,
Ta5d6ff"Ta5d6ffclient_propagation_messages_servedTa5d6ff"Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffclient_propagation_messages_servedTb4b4b4,
Ta5d6ff"Ta5d6ffunpeered_propagation_incomingTa5d6ff"Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffunpeered_propagation_incomingTb4b4b4,
Ta5d6ff"Ta5d6ffunpeered_propagation_rx_bytesTa5d6ff"Tb4b4b4: Tff7b72selfTff7b72.Td2a8ffunpeered_propagation_rx_bytesTb4b4b4,
Tb4b4b4}
Te6edf3stats_fileTff7b72.Td2a8ffwriteTb4b4b4(Te6edf3msgpackTff7b72.Td2a8ffpackbTb4b4b4(Te6edf3node_statsTb4b4b4)Tb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCould not save local node stats to storage. The contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72def Td2a8ffclean_outbound_stamp_costsTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72tryTb4b4b4:
Te6edf3expired Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72for Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffoutbound_stamp_costsTb4b4b4:
Te6edf3entry Tff7b72= Tff7b72selfTff7b72.Td2a8ffoutbound_stamp_costsTb4b4b4[Te6edf3destination_hashTb4b4b4]
Tff7b72if Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72> Te6edf3entryTb4b4b4[T79c0ff0Tb4b4b4] Tff7b72+ Te6edf3LXMRouterTff7b72.Td2a8ffSTAMP_COST_EXPIRYTb4b4b4:
Te6edf3expiredTff7b72.Td2a8ffappendTb4b4b4(Te6edf3destination_hashTb4b4b4)
Tff7b72for Te6edf3destination_hash Tff7b72in Te6edf3expiredTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffoutbound_stamp_costsTff7b72.Td2a8ffpopTb4b4b4(Te6edf3destination_hashTb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffError while cleaning outbound stamp costs. The contained exception was: Tffd700{Te6edf3eTffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Te6edf3RNSTff7b72.Td2a8fftrace_exceptionTb4b4b4(Te6edf3eTb4b4b4)
Tff7b72def Td2a8ffsave_outbound_stamp_costsTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72with Tff7b72selfTff7b72.Td2a8ffcost_file_lockTb4b4b4:
Tff7b72tryTb4b4b4:
Tff7b72if Tff7b72not Te6edf3osTff7b72.Td2a8ffpathTff7b72.Td2a8ffisdirTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTb4b4b4)Tb4b4b4:
Te6edf3osTff7b72.Td2a8ffmakedirsTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTb4b4b4)
Te6edf3outbound_stamp_costs_file Tff7b72= Tffa657openTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTff7b72+Ta5d6ff"Ta5d6ff/outbound_stamp_costsTa5d6ff"Tb4b4b4, Ta5d6ff"Ta5d6ffwbTa5d6ff"Tb4b4b4)
Te6edf3outbound_stamp_costs_fileTff7b72.Td2a8ffwriteTb4b4b4(Te6edf3msgpackTff7b72.Td2a8ffpackbTb4b4b4(Tff7b72selfTff7b72.Td2a8ffoutbound_stamp_costsTb4b4b4)Tb4b4b4)
Te6edf3outbound_stamp_costs_fileTff7b72.Td2a8ffcloseTb4b4b4(Tb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCould not save outbound stamp costs to storage. The contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72def Td2a8ffclean_available_ticketsTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72tryTb4b4b4:
T8b949e# Clean outbound tickets
Te6edf3expired_outbound Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72for Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffoutboundTa5d6ff"Tb4b4b4]Tb4b4b4:
Te6edf3entry Tff7b72= Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffoutboundTa5d6ff"Tb4b4b4]Tb4b4b4[Te6edf3destination_hashTb4b4b4]
Tff7b72if Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72> Te6edf3entryTb4b4b4[T79c0ff0Tb4b4b4]Tb4b4b4:
Te6edf3expired_outboundTff7b72.Td2a8ffappendTb4b4b4(Te6edf3destination_hashTb4b4b4)
Tff7b72for Te6edf3destination_hash Tff7b72in Te6edf3expired_outboundTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffoutboundTa5d6ff"Tb4b4b4]Tff7b72.Td2a8ffpopTb4b4b4(Te6edf3destination_hashTb4b4b4)
T8b949e# Clean inbound tickets
Tff7b72for Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffinboundTa5d6ff"Tb4b4b4]Tb4b4b4:
Te6edf3expired_inbound Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72for Te6edf3inbound_ticket Tff7b72in Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffinboundTa5d6ff"Tb4b4b4]Tb4b4b4[Te6edf3destination_hashTb4b4b4]Tb4b4b4:
Te6edf3entry Tff7b72= Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffinboundTa5d6ff"Tb4b4b4]Tb4b4b4[Te6edf3destination_hashTb4b4b4]Tb4b4b4[Te6edf3inbound_ticketTb4b4b4]
Te6edf3ticket_expiry Tff7b72= Te6edf3entryTb4b4b4[T79c0ff0Tb4b4b4]
Tff7b72if Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72> Te6edf3ticket_expiryTff7b72+Te6edf3LXMessageTff7b72.Td2a8ffTICKET_GRACETb4b4b4:
Te6edf3expired_inboundTff7b72.Td2a8ffappendTb4b4b4(Te6edf3inbound_ticketTb4b4b4)
Tff7b72for Te6edf3inbound_ticket Tff7b72in Te6edf3expired_inboundTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffinboundTa5d6ff"Tb4b4b4]Tb4b4b4[Te6edf3destination_hashTb4b4b4]Tff7b72.Td2a8ffpopTb4b4b4(Te6edf3inbound_ticketTb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffError while cleaning available tickets. The contained exception was: Tffd700{Te6edf3eTffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Te6edf3RNSTff7b72.Td2a8fftrace_exceptionTb4b4b4(Te6edf3eTb4b4b4)
Tff7b72def Td2a8ffsave_available_ticketsTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72with Tff7b72selfTff7b72.Td2a8ffticket_file_lockTb4b4b4:
Tff7b72tryTb4b4b4:
Tff7b72if Tff7b72not Te6edf3osTff7b72.Td2a8ffpathTff7b72.Td2a8ffisdirTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTb4b4b4)Tb4b4b4:
Te6edf3osTff7b72.Td2a8ffmakedirsTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTb4b4b4)
Te6edf3available_tickets_file Tff7b72= Tffa657openTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTff7b72+Ta5d6ff"Ta5d6ff/available_ticketsTa5d6ff"Tb4b4b4, Ta5d6ff"Ta5d6ffwbTa5d6ff"Tb4b4b4)
Te6edf3available_tickets_fileTff7b72.Td2a8ffwriteTb4b4b4(Te6edf3msgpackTff7b72.Td2a8ffpackbTb4b4b4(Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4)Tb4b4b4)
Te6edf3available_tickets_fileTff7b72.Td2a8ffcloseTb4b4b4(Tb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCould not save available tickets to storage. The contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72def Td2a8ffreload_available_ticketsTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffReloading available tickets from storageTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72tryTb4b4b4:
Tff7b72with Tff7b72selfTff7b72.Td2a8ffticket_file_lockTb4b4b4:
Tff7b72with Tffa657openTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTff7b72+Ta5d6ff"Ta5d6ff/available_ticketsTa5d6ff"Tb4b4b4, Ta5d6ff"Ta5d6ffrbTa5d6ff"Tb4b4b4) Tff7b72as Te6edf3available_tickets_fileTb4b4b4:
Te6edf3data Tff7b72= Te6edf3available_tickets_fileTff7b72.Td2a8ffreadTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffavailable_tickets Tff7b72= Te6edf3msgpackTff7b72.Td2a8ffunpackbTb4b4b4(Te6edf3dataTb4b4b4)
Tff7b72if Tff7b72not Tffa657typeTb4b4b4(Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4) Tff7b72== Tffa657dictTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffInvalid data format for loaded available tickets, recreating...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffavailable_tickets Tff7b72= Tb4b4b4{Ta5d6ff"Ta5d6ffoutboundTa5d6ff"Tb4b4b4: Tb4b4b4{Tb4b4b4}Tb4b4b4, Ta5d6ff"Ta5d6ffinboundTa5d6ff"Tb4b4b4: Tb4b4b4{Tb4b4b4}Tb4b4b4, Ta5d6ff"Ta5d6fflast_deliveriesTa5d6ff"Tb4b4b4: Tb4b4b4{Tb4b4b4}Tb4b4b4}
Tff7b72if Tff7b72not Ta5d6ff"Ta5d6ffoutboundTa5d6ff" Tff7b72in Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffMissing outbound entry in loaded available tickets, recreating...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffoutboundTa5d6ff"Tb4b4b4] Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72if Tff7b72not Ta5d6ff"Ta5d6ffinboundTa5d6ff" Tff7b72in Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffMissing inbound entry in loaded available tickets, recreating...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6ffinboundTa5d6ff"Tb4b4b4] Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72if Tff7b72not Ta5d6ff"Ta5d6fflast_deliveriesTa5d6ff" Tff7b72in Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffMissing local_deliveries entry in loaded available tickets, recreating...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6fflast_deliveriesTa5d6ff"Tb4b4b4] Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffAn error occurred while reloading available tickets from storage: Tffd700{Te6edf3eTffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72def Td2a8ffexit_handlerTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8ffexit_handler_runningTb4b4b4:
Tff7b72return
Tff7b72selfTff7b72.Td2a8ffexit_handler_running Tff7b72= Tff7b72True
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffTearing down delivery destinations...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_NOTICETb4b4b4)
Tff7b72for Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffdelivery_destinationsTb4b4b4:
Te6edf3delivery_destination Tff7b72= Tff7b72selfTff7b72.Td2a8ffdelivery_destinationsTb4b4b4[Te6edf3destination_hashTb4b4b4]
Te6edf3delivery_destinationTff7b72.Td2a8ffset_packet_callbackTb4b4b4(Tff7b72NoneTb4b4b4)
Te6edf3delivery_destinationTff7b72.Td2a8ffset_link_established_callbackTb4b4b4(Tff7b72NoneTb4b4b4)
Tff7b72for Te6edf3link Tff7b72in Te6edf3delivery_destinationTff7b72.Td2a8fflinksTb4b4b4:
Tff7b72tryTb4b4b4:
Tff7b72if Te6edf3linkTff7b72.Td2a8ffstatus Tff7b72== Te6edf3RNSTff7b72.Td2a8ffLinkTff7b72.Td2a8ffACTIVETb4b4b4:
Te6edf3linkTff7b72.Td2a8ffteardownTb4b4b4(Tb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffError while tearing down propagation link: Tffd700{e}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72if Tff7b72selfTff7b72.Td2a8ffpropagation_nodeTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffTearing down propagation node destination...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_NOTICETb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_destinationTff7b72.Td2a8ffset_link_established_callbackTb4b4b4(Tff7b72NoneTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_destinationTff7b72.Td2a8ffset_packet_callbackTb4b4b4(Tff7b72NoneTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_destinationTff7b72.Td2a8ffderegister_request_handlerTb4b4b4(Te6edf3LXMPeerTff7b72.Td2a8ffOFFER_REQUEST_PATHTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_destinationTff7b72.Td2a8ffderegister_request_handlerTb4b4b4(Te6edf3LXMPeerTff7b72.Td2a8ffMESSAGE_GET_PATHTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_destinationTff7b72.Td2a8ffderegister_request_handlerTb4b4b4(Te6edf3LXMRouterTff7b72.Td2a8ffSTATS_GET_PATHTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_destinationTff7b72.Td2a8ffderegister_request_handlerTb4b4b4(Te6edf3LXMRouterTff7b72.Td2a8ffSYNC_REQUEST_PATHTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_destinationTff7b72.Td2a8ffderegister_request_handlerTb4b4b4(Te6edf3LXMRouterTff7b72.Td2a8ffUNPEER_REQUEST_PATHTb4b4b4)
Tff7b72for Te6edf3link Tff7b72in Tff7b72selfTff7b72.Td2a8ffactive_propagation_linksTb4b4b4:
Tff7b72tryTb4b4b4:
Tff7b72if Te6edf3linkTff7b72.Td2a8ffstatus Tff7b72== Te6edf3RNSTff7b72.Td2a8ffLinkTff7b72.Td2a8ffACTIVETb4b4b4:
Te6edf3linkTff7b72.Td2a8ffteardownTb4b4b4(Tb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffError while tearing down propagation link: Tffd700{e}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffPersisting LXMF state data to storage...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_NOTICETb4b4b4)
Tff7b72selfTff7b72.Td2a8ffflush_queuesTb4b4b4(Tb4b4b4)
Tff7b72if Tff7b72selfTff7b72.Td2a8ffpropagation_nodeTb4b4b4:
Tff7b72tryTb4b4b4:
Te6edf3st Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)Tb4b4b4; Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffSaving Tffd700{Tffa657lenTb4b4b4(Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4)Tffd700}Ta5d6ff peer synchronisation states to storage...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_NOTICETb4b4b4)
Te6edf3serialised_peers Tff7b72= Tb4b4b4[Tb4b4b4]
Te6edf3peer_dict Tff7b72= Tff7b72selfTff7b72.Td2a8ffpeersTff7b72.Td2a8ffcopyTb4b4b4(Tb4b4b4)
Tff7b72for Te6edf3peer_id Tff7b72in Te6edf3peer_dictTb4b4b4:
Te6edf3peer Tff7b72= Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4[Te6edf3peer_idTb4b4b4]
Te6edf3serialised_peersTff7b72.Td2a8ffappendTb4b4b4(Te6edf3peerTff7b72.Td2a8ffto_bytesTb4b4b4(Tb4b4b4)Tb4b4b4)
Te6edf3peers_file Tff7b72= Tffa657openTb4b4b4(Tff7b72selfTff7b72.Td2a8ffstoragepathTff7b72+Ta5d6ff"Ta5d6ff/peersTa5d6ff"Tb4b4b4, Ta5d6ff"Ta5d6ffwbTa5d6ff"Tb4b4b4)
Te6edf3peers_fileTff7b72.Td2a8ffwriteTb4b4b4(Te6edf3msgpackTff7b72.Td2a8ffpackbTb4b4b4(Te6edf3serialised_peersTb4b4b4)Tb4b4b4)
Te6edf3peers_fileTff7b72.Td2a8ffcloseTb4b4b4(Tb4b4b4)
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffSaved Tffd700{Tffa657lenTb4b4b4(Te6edf3serialised_peersTb4b4b4)Tffd700}Ta5d6ff peers to storage in Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettyshorttimeTb4b4b4(Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)Tff7b72-Te6edf3stTb4b4b4)Tffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_NOTICETb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCould not save propagation node peers to storage. The contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffsave_locally_delivered_transient_idsTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffsave_locally_processed_transient_idsTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffsave_node_statsTb4b4b4(Tb4b4b4)
Tff7b72def Td2a8ffsigint_handlerTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3signalTb4b4b4, Te6edf3frameTb4b4b4)Tb4b4b4:
Tff7b72if Tff7b72not Tff7b72selfTff7b72.Td2a8ffexit_handler_runningTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffReceived SIGINT, shutting down now!Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_WARNINGTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffexit_handlerTb4b4b4(Tb4b4b4)
Te6edf3RNSTff7b72.Td2a8ffexitTb4b4b4(T79c0ff0Tb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffReceived SIGINT, but exit handler is running, keeping process alive until storage persist is completeTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_WARNINGTb4b4b4)
Tff7b72def Td2a8ffsigterm_handlerTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3signalTb4b4b4, Te6edf3frameTb4b4b4)Tb4b4b4:
Tff7b72if Tff7b72not Tff7b72selfTff7b72.Td2a8ffexit_handler_runningTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffReceived SIGTERM, shutting down now!Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_WARNINGTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffexit_handlerTb4b4b4(Tb4b4b4)
Te6edf3RNSTff7b72.Td2a8ffexitTb4b4b4(T79c0ff0Tb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffReceived SIGTERM, but exit handler is running, keeping process alive until storage persist is completeTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_WARNINGTb4b4b4)
Tff7b72def Tff7b72__str__Tb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72return Ta5d6ff"Ta5d6ff<LXMRouter Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffhexrepTb4b4b4(Tff7b72selfTff7b72.Td2a8ffidentityTff7b72.Td2a8ffhashTb4b4b4, Te6edf3delimitTff7b72=Tff7b72FalseTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff>Ta5d6ff"
T8b949e### Message Download ##################################
T8b949e#######################################################
Tff7b72def Td2a8ffrequest_messages_path_jobTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Te6edf3job_thread Tff7b72= Te6edf3threadingTff7b72.Td2a8ffThreadTb4b4b4(Te6edf3targetTff7b72=Tff7b72selfTff7b72.Td2a8ff__request_messages_path_jobTb4b4b4)
Te6edf3job_threadTff7b72.Td2a8ffsetDaemonTb4b4b4(Tff7b72TrueTb4b4b4)
Te6edf3job_threadTff7b72.Td2a8ffstartTb4b4b4(Tb4b4b4)
Tff7b72def Td2a8ff__request_messages_path_jobTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Te6edf3path_timeout Tff7b72= Tff7b72selfTff7b72.Td2a8ffwants_download_on_path_available_timeout
Tff7b72while Tff7b72not Te6edf3RNSTff7b72.Td2a8ffTransportTff7b72.Td2a8ffhas_pathTb4b4b4(Tff7b72selfTff7b72.Td2a8ffwants_download_on_path_available_fromTb4b4b4) Tff7b72and Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72< Te6edf3path_timeoutTb4b4b4:
Te6edf3timeTff7b72.Td2a8ffsleepTb4b4b4(T79c0ff0.1Tb4b4b4)
Tff7b72if Te6edf3RNSTff7b72.Td2a8ffTransportTff7b72.Td2a8ffhas_pathTb4b4b4(Tff7b72selfTff7b72.Td2a8ffwants_download_on_path_available_fromTb4b4b4)Tb4b4b4:
Tff7b72selfTff7b72.Td2a8ffrequest_messages_from_propagation_nodeTb4b4b4(Tff7b72selfTff7b72.Td2a8ffwants_download_on_path_available_toTb4b4b4, Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_max_messagesTb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffPropagation node path request timed outTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffacknowledge_sync_completionTb4b4b4(Te6edf3failure_stateTff7b72=Te6edf3LXMRouterTff7b72.Td2a8ffPR_NO_PATHTb4b4b4)
Tff7b72def Td2a8ffidentity_allowedTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3identityTb4b4b4)Tb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8ffauth_requiredTb4b4b4:
Tff7b72if Te6edf3identityTff7b72.Td2a8ffhash Tff7b72in Tff7b72selfTff7b72.Td2a8ffallowed_listTb4b4b4:
Tff7b72return Tff7b72True
Tff7b72elseTb4b4b4:
Tff7b72return Tff7b72False
Tff7b72elseTb4b4b4:
Tff7b72return Tff7b72True
Tff7b72def Td2a8ffmessage_get_requestTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3pathTb4b4b4, Te6edf3dataTb4b4b4, Te6edf3request_idTb4b4b4, Te6edf3remote_identityTb4b4b4, Te6edf3requested_atTb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3remote_identity Tff7b72== Tff7b72NoneTb4b4b4: Tff7b72return Te6edf3LXMPeerTff7b72.Td2a8ffERROR_NO_IDENTITY
Tff7b72elif Tff7b72not Tff7b72selfTff7b72.Td2a8ffidentity_allowedTb4b4b4(Te6edf3remote_identityTb4b4b4)Tb4b4b4: Tff7b72return Te6edf3LXMPeerTff7b72.Td2a8ffERROR_NO_ACCESS
Tff7b72elseTb4b4b4:
Tff7b72tryTb4b4b4:
Te6edf3remote_destination Tff7b72= Te6edf3RNSTff7b72.Td2a8ffDestinationTb4b4b4(Te6edf3remote_identityTb4b4b4, Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffOUTTb4b4b4, Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffSINGLETb4b4b4, Te6edf3APP_NAMETb4b4b4, Ta5d6ff"Ta5d6ffdeliveryTa5d6ff"Tb4b4b4)
T8b949e# If both want and have fields are empty, send a list of
T8b949e# available messages.
Tff7b72if Te6edf3dataTb4b4b4[T79c0ff0Tb4b4b4] Tff7b72== Tff7b72None Tff7b72and Te6edf3dataTb4b4b4[T79c0ff1Tb4b4b4] Tff7b72== Tff7b72NoneTb4b4b4:
Te6edf3available_messages Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72for Te6edf3transient_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTb4b4b4:
Te6edf3message_entry Tff7b72= Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTb4b4b4[Te6edf3transient_idTb4b4b4]
Tff7b72if Te6edf3message_entryTb4b4b4[T79c0ff0Tb4b4b4] Tff7b72== Te6edf3remote_destinationTff7b72.Td2a8ffhashTb4b4b4:
Te6edf3message_size Tff7b72= Te6edf3osTff7b72.Td2a8ffpathTff7b72.Td2a8ffgetsizeTb4b4b4(Te6edf3message_entryTb4b4b4[T79c0ff1Tb4b4b4]Tb4b4b4)
Te6edf3available_entry Tff7b72= Tb4b4b4[Te6edf3transient_idTb4b4b4, Te6edf3message_sizeTb4b4b4]
Te6edf3available_messagesTff7b72.Td2a8ffappendTb4b4b4(Te6edf3available_entryTb4b4b4)
Te6edf3available_messagesTff7b72.Td2a8ffsortTb4b4b4(Te6edf3keyTff7b72=Tff7b72lambda Te6edf3eTb4b4b4: Te6edf3eTb4b4b4[T79c0ff1Tb4b4b4]Tb4b4b4, Te6edf3reverseTff7b72=Tff7b72FalseTb4b4b4)
Te6edf3transient_ids Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72for Te6edf3available_entry Tff7b72in Te6edf3available_messagesTb4b4b4: Te6edf3transient_idsTff7b72.Td2a8ffappendTb4b4b4(Te6edf3available_entryTb4b4b4[T79c0ff0Tb4b4b4]Tb4b4b4)
Tff7b72return Te6edf3transient_ids
Tff7b72elseTb4b4b4:
T8b949e# Process messages the client already have
Tff7b72if Te6edf3dataTb4b4b4[T79c0ff1Tb4b4b4] Tff7b72!= Tff7b72None Tff7b72and Tffa657lenTb4b4b4(Te6edf3dataTb4b4b4[T79c0ff1Tb4b4b4]Tb4b4b4) Tff7b72> T79c0ff0Tb4b4b4:
Tff7b72for Te6edf3transient_id Tff7b72in Te6edf3dataTb4b4b4[T79c0ff1Tb4b4b4]Tb4b4b4:
Tff7b72if Te6edf3transient_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffpropagation_entries Tff7b72and Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTb4b4b4[Te6edf3transient_idTb4b4b4]Tb4b4b4[T79c0ff0Tb4b4b4] Tff7b72== Te6edf3remote_destinationTff7b72.Td2a8ffhashTb4b4b4:
Tff7b72tryTb4b4b4:
Te6edf3filepath Tff7b72= Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTb4b4b4[Te6edf3transient_idTb4b4b4]Tb4b4b4[T79c0ff1Tb4b4b4]
Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTff7b72.Td2a8ffpopTb4b4b4(Te6edf3transient_idTb4b4b4)
Te6edf3osTff7b72.Td2a8ffunlinkTb4b4b4(Te6edf3filepathTb4b4b4)
T8b949e# TODO: Remove debug
T8b949e# RNS.log("Client "+RNS.prettyhexrep(remote_destination.hash)+" purged message "+RNS.prettyhexrep(transient_id)+" at "+str(filepath), RNS.LOG_DEBUG)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffError while processing message purge request from Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3remote_destinationTff7b72.Td2a8ffhashTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff. The contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
T8b949e# Process wanted messages
Te6edf3response_messages Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72if Te6edf3dataTb4b4b4[T79c0ff0Tb4b4b4] Tff7b72!= Tff7b72None Tff7b72and Tffa657lenTb4b4b4(Te6edf3dataTb4b4b4[T79c0ff0Tb4b4b4]Tb4b4b4) Tff7b72> T79c0ff0Tb4b4b4:
Te6edf3client_transfer_limit Tff7b72= Tff7b72None
Tff7b72if Tffa657lenTb4b4b4(Te6edf3dataTb4b4b4) Tff7b72>Tff7b72= T79c0ff3Tb4b4b4:
Tff7b72tryTb4b4b4:
Te6edf3client_transfer_limit Tff7b72= Tffa657floatTb4b4b4(Te6edf3dataTb4b4b4[T79c0ff2Tb4b4b4]Tb4b4b4)Tff7b72*T79c0ff1000
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffClient indicates transfer limit of Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettysizeTb4b4b4(Te6edf3client_transfer_limitTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72exceptTb4b4b4: Tff7b72pass
Te6edf3per_message_overhead Tff7b72= T79c0ff16 T8b949e# Really only 2 bytes, but set a bit higher for now
Te6edf3cumulative_size Tff7b72= T79c0ff24 T8b949e# Initialised to highest reasonable binary structure overhead
Tff7b72for Te6edf3transient_id Tff7b72in Te6edf3dataTb4b4b4[T79c0ff0Tb4b4b4]Tb4b4b4:
Tff7b72if Te6edf3transient_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffpropagation_entries Tff7b72and Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTb4b4b4[Te6edf3transient_idTb4b4b4]Tb4b4b4[T79c0ff0Tb4b4b4] Tff7b72== Te6edf3remote_destinationTff7b72.Td2a8ffhashTb4b4b4:
Tff7b72tryTb4b4b4:
Te6edf3filepath Tff7b72= Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTb4b4b4[Te6edf3transient_idTb4b4b4]Tb4b4b4[T79c0ff1Tb4b4b4]
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffClient Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3remote_destinationTff7b72.Td2a8ffhashTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff requested message Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3transient_idTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff at Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3filepathTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3message_file Tff7b72= Tffa657openTb4b4b4(Te6edf3filepathTb4b4b4, Ta5d6ff"Ta5d6ffrbTa5d6ff"Tb4b4b4)
Te6edf3lxmf_data Tff7b72= Te6edf3message_fileTff7b72.Td2a8ffreadTb4b4b4(Tb4b4b4)
Te6edf3message_fileTff7b72.Td2a8ffcloseTb4b4b4(Tb4b4b4)
Te6edf3lxm_size Tff7b72= Tffa657lenTb4b4b4(Te6edf3lxmf_dataTb4b4b4)
Te6edf3next_size Tff7b72= Te6edf3cumulative_size Tff7b72+ Tb4b4b4(Te6edf3lxm_sizeTff7b72+Te6edf3per_message_overheadTb4b4b4)
Tff7b72if Te6edf3client_transfer_limit Tff7b72!= Tff7b72None Tff7b72and Te6edf3next_size Tff7b72> Te6edf3client_transfer_limitTb4b4b4: Tff7b72pass
Tff7b72elseTb4b4b4:
Te6edf3response_messagesTff7b72.Td2a8ffappendTb4b4b4(Te6edf3lxmf_dataTb4b4b4[Tb4b4b4:Tff7b72-Te6edf3LXStamperTff7b72.Td2a8ffSTAMP_SIZETb4b4b4]Tb4b4b4)
Te6edf3cumulative_size Tff7b72+Tff7b72= Tb4b4b4(Te6edf3lxm_sizeTff7b72+Te6edf3per_message_overheadTb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffError while processing message download request from Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3remote_destinationTff7b72.Td2a8ffhashTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff. The contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffclient_propagation_messages_served Tff7b72+Tff7b72= Tffa657lenTb4b4b4(Te6edf3response_messagesTb4b4b4)
Tff7b72return Te6edf3response_messages
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffError occurred while generating response for download request, the contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72return Tff7b72None
Tff7b72def Td2a8ffmessage_list_responseTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3request_receiptTb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3request_receiptTff7b72.Td2a8ffresponse Tff7b72== Te6edf3LXMPeerTff7b72.Td2a8ffERROR_NO_IDENTITYTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffPropagation node indicated missing identification on list request, tearing down link.Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72if Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_link Tff7b72!= Tff7b72NoneTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_linkTff7b72.Td2a8ffteardownTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_state Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffPR_NO_IDENTITY_RCVD
Tff7b72elif Te6edf3request_receiptTff7b72.Td2a8ffresponse Tff7b72== Te6edf3LXMPeerTff7b72.Td2a8ffERROR_NO_ACCESSTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffPropagation node did not allow list request, tearing down link.Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72if Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_link Tff7b72!= Tff7b72NoneTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_linkTff7b72.Td2a8ffteardownTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_state Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffPR_NO_ACCESS
Tff7b72elseTb4b4b4:
Tff7b72if Te6edf3request_receiptTff7b72.Td2a8ffresponse Tff7b72!= Tff7b72None Tff7b72and Tffa657isinstanceTb4b4b4(Te6edf3request_receiptTff7b72.Td2a8ffresponseTb4b4b4, Tffa657listTb4b4b4)Tb4b4b4:
Te6edf3haves Tff7b72= Tb4b4b4[Tb4b4b4]
Te6edf3wants Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72if Tffa657lenTb4b4b4(Te6edf3request_receiptTff7b72.Td2a8ffresponseTb4b4b4) Tff7b72> T79c0ff0Tb4b4b4:
Tff7b72for Te6edf3transient_id Tff7b72in Te6edf3request_receiptTff7b72.Td2a8ffresponseTb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8ffhas_messageTb4b4b4(Te6edf3transient_idTb4b4b4)Tb4b4b4:
Tff7b72if Tff7b72not Tff7b72selfTff7b72.Td2a8ffretain_synced_on_nodeTb4b4b4:
Te6edf3havesTff7b72.Td2a8ffappendTb4b4b4(Te6edf3transient_idTb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_max_messages Tff7b72== Te6edf3LXMRouterTff7b72.Td2a8ffPR_ALL_MESSAGES Tff7b72or Tffa657lenTb4b4b4(Te6edf3wantsTb4b4b4) Tff7b72< Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_max_messagesTb4b4b4:
Te6edf3wantsTff7b72.Td2a8ffappendTb4b4b4(Te6edf3transient_idTb4b4b4)
Te6edf3ms Tff7b72= Ta5d6ff"Ta5d6ff" Tff7b72if Tffa657lenTb4b4b4(Te6edf3wantsTb4b4b4) Tff7b72== T79c0ff1 Tff7b72else Ta5d6ff"Ta5d6ffsTa5d6ff"
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffRequesting Tffd700{Tffa657lenTb4b4b4(Te6edf3wantsTb4b4b4)Tffd700}Ta5d6ff messageTffd700{Te6edf3msTffd700}Ta5d6ff from propagation nodeTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3request_receiptTff7b72.Td2a8fflinkTff7b72.Td2a8ffrequestTb4b4b4(
Te6edf3LXMPeerTff7b72.Td2a8ffMESSAGE_GET_PATHTb4b4b4,
Tb4b4b4[Te6edf3wantsTb4b4b4, Te6edf3havesTb4b4b4, Tff7b72selfTff7b72.Td2a8ffdelivery_per_transfer_limitTb4b4b4]Tb4b4b4,
Te6edf3response_callbackTff7b72=Tff7b72selfTff7b72.Td2a8ffmessage_get_responseTb4b4b4,
Te6edf3failed_callbackTff7b72=Tff7b72selfTff7b72.Td2a8ffmessage_get_failedTb4b4b4,
Te6edf3progress_callbackTff7b72=Tff7b72selfTff7b72.Td2a8ffmessage_get_progressTb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_state Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffPR_COMPLETE
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_progress Tff7b72= T79c0ff1.0
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_last_result Tff7b72= T79c0ff0
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffInvalid message list data received from propagation nodeTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72if Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_link Tff7b72!= Tff7b72NoneTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_linkTff7b72.Td2a8ffteardownTb4b4b4(Tb4b4b4)
Tff7b72def Td2a8ffmessage_get_responseTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3request_receiptTb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3request_receiptTff7b72.Td2a8ffresponse Tff7b72== Te6edf3LXMPeerTff7b72.Td2a8ffERROR_NO_IDENTITYTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffPropagation node indicated missing identification on get request, tearing down link.Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72if Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_link Tff7b72!= Tff7b72NoneTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_linkTff7b72.Td2a8ffteardownTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_state Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffPR_NO_IDENTITY_RCVD
Tff7b72elif Te6edf3request_receiptTff7b72.Td2a8ffresponse Tff7b72== Te6edf3LXMPeerTff7b72.Td2a8ffERROR_NO_ACCESSTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffPropagation node did not allow get request, tearing down link.Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72if Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_link Tff7b72!= Tff7b72NoneTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_linkTff7b72.Td2a8ffteardownTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_state Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffPR_NO_ACCESS
Tff7b72elseTb4b4b4:
Te6edf3duplicates Tff7b72= T79c0ff0
Tff7b72if Te6edf3request_receiptTff7b72.Td2a8ffresponse Tff7b72!= Tff7b72None Tff7b72and Tffa657lenTb4b4b4(Te6edf3request_receiptTff7b72.Td2a8ffresponseTb4b4b4) Tff7b72> T79c0ff0Tb4b4b4:
Te6edf3haves Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72for Te6edf3lxmf_data Tff7b72in Te6edf3request_receiptTff7b72.Td2a8ffresponseTb4b4b4:
Te6edf3result Tff7b72= Tff7b72selfTff7b72.Td2a8fflxmf_propagationTb4b4b4(Te6edf3lxmf_dataTb4b4b4, Te6edf3signal_duplicateTff7b72=Te6edf3LXMRouterTff7b72.Td2a8ffDUPLICATE_SIGNALTb4b4b4)
Tff7b72if Te6edf3result Tff7b72== Te6edf3LXMRouterTff7b72.Td2a8ffDUPLICATE_SIGNALTb4b4b4: Te6edf3duplicates Tff7b72+Tff7b72= T79c0ff1
Te6edf3havesTff7b72.Td2a8ffappendTb4b4b4(Te6edf3RNSTff7b72.Td2a8ffIdentityTff7b72.Td2a8fffull_hashTb4b4b4(Te6edf3lxmf_dataTb4b4b4)Tb4b4b4)
T8b949e# Return a list of successfully received messages to the node.
T8b949e# This deletes the messages on the propagation node.
T8b949e# TODO: Add option to keep messages on node.
Te6edf3request_receiptTff7b72.Td2a8fflinkTff7b72.Td2a8ffrequestTb4b4b4(
Te6edf3LXMPeerTff7b72.Td2a8ffMESSAGE_GET_PATHTb4b4b4,
Tb4b4b4[Tff7b72NoneTb4b4b4, Te6edf3havesTb4b4b4]Tb4b4b4,
T8b949e# response_callback=self.message_syncfinal_response,
Te6edf3failed_callbackTff7b72=Tff7b72selfTff7b72.Td2a8ffmessage_get_failedTb4b4b4,
T8b949e# progress_callback=self.message_get_progress
Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_state Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffPR_COMPLETE
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_progress Tff7b72= T79c0ff1.0
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_last_duplicates Tff7b72= Te6edf3duplicates
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_last_result Tff7b72= Tffa657lenTb4b4b4(Te6edf3request_receiptTff7b72.Td2a8ffresponseTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffsave_locally_delivered_transient_idsTb4b4b4(Tb4b4b4)
Tff7b72def Td2a8ffmessage_get_progressTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3request_receiptTb4b4b4)Tb4b4b4:
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_state Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffPR_RECEIVING
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_progress Tff7b72= Te6edf3request_receiptTff7b72.Td2a8ffget_progressTb4b4b4(Tb4b4b4)
Tff7b72def Td2a8ffmessage_get_failedTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3request_receiptTb4b4b4)Tb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffMessage list/get request failedTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72if Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_link Tff7b72!= Tff7b72NoneTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_linkTff7b72.Td2a8ffteardownTb4b4b4(Tb4b4b4)
Tff7b72def Td2a8ffacknowledge_sync_completionTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3reset_stateTff7b72=Tff7b72FalseTb4b4b4, Te6edf3failure_stateTff7b72=Tff7b72NoneTb4b4b4)Tb4b4b4:
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_last_result Tff7b72= Tff7b72None
Tff7b72if Te6edf3reset_state Tff7b72or Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_state Tff7b72<Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffPR_COMPLETETb4b4b4:
Tff7b72if Te6edf3failure_state Tff7b72== Tff7b72NoneTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_state Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffPR_IDLE
Tff7b72elseTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_state Tff7b72= Te6edf3failure_state
Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_progress Tff7b72= T79c0ff0.0
Tff7b72selfTff7b72.Td2a8ffwants_download_on_path_available_from Tff7b72= Tff7b72None
Tff7b72selfTff7b72.Td2a8ffwants_download_on_path_available_to Tff7b72= Tff7b72None
Tff7b72def Td2a8ffhas_messageTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3transient_idTb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3transient_id Tff7b72in Tff7b72selfTff7b72.Td2a8fflocally_delivered_transient_idsTb4b4b4:
Tff7b72return Tff7b72True
Tff7b72elseTb4b4b4:
Tff7b72return Tff7b72False
Tff7b72def Td2a8ffcancel_outboundTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3message_idTb4b4b4, Te6edf3cancel_stateTff7b72=Te6edf3LXMessageTff7b72.Td2a8ffCANCELLEDTb4b4b4)Tb4b4b4:
Tff7b72tryTb4b4b4:
Tff7b72if Te6edf3message_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffpending_deferred_stampsTb4b4b4:
Te6edf3lxm Tff7b72= Tff7b72selfTff7b72.Td2a8ffpending_deferred_stampsTb4b4b4[Te6edf3message_idTb4b4b4]
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffCancelling deferred stamp generation for Tffd700{Te6edf3lxmTffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3lxmTff7b72.Td2a8ffstate Tff7b72= Te6edf3cancel_state
Te6edf3LXStamperTff7b72.Td2a8ffcancel_workTb4b4b4(Te6edf3message_idTb4b4b4)
Te6edf3lxmessage Tff7b72= Tff7b72None
Tff7b72for Te6edf3lxm Tff7b72in Tff7b72selfTff7b72.Td2a8ffpending_outboundTb4b4b4:
Tff7b72if Te6edf3lxmTff7b72.Td2a8ffmessage_id Tff7b72== Te6edf3message_idTb4b4b4:
Te6edf3lxmessage Tff7b72= Te6edf3lxm
Tff7b72if Te6edf3lxmessage Tff7b72!= Tff7b72NoneTb4b4b4:
Te6edf3lxmessageTff7b72.Td2a8ffstate Tff7b72= Te6edf3cancel_state
Tff7b72if Te6edf3lxmessage Tff7b72in Tff7b72selfTff7b72.Td2a8ffpending_outboundTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffCancelling Tffd700{Te6edf3lxmessageTffd700}Ta5d6ff in outbound queueTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8ffrepresentation Tff7b72== Te6edf3LXMessageTff7b72.Td2a8ffRESOURCETb4b4b4:
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8ffresource_representation Tff7b72!= Tff7b72NoneTb4b4b4:
Te6edf3lxmessageTff7b72.Td2a8ffresource_representationTff7b72.Td2a8ffcancelTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffprocess_outboundTb4b4b4(Tb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffAn error occurred while cancelling Tffd700{Te6edf3lxmessageTffd700}Ta5d6ff: Tffd700{Te6edf3eTffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Te6edf3RNSTff7b72.Td2a8fftrace_exceptionTb4b4b4(Te6edf3eTb4b4b4)
Tff7b72def Td2a8ffhandle_outboundTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3lxmessageTb4b4b4)Tb4b4b4:
Te6edf3destination_hash Tff7b72= Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhash
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8ffstamp_cost Tff7b72== Tff7b72NoneTb4b4b4:
Tff7b72if Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffoutbound_stamp_costsTb4b4b4:
Te6edf3stamp_cost Tff7b72= Tff7b72selfTff7b72.Td2a8ffoutbound_stamp_costsTb4b4b4[Te6edf3destination_hashTb4b4b4]Tb4b4b4[T79c0ff1Tb4b4b4]
Te6edf3lxmessageTff7b72.Td2a8ffstamp_cost Tff7b72= Te6edf3stamp_cost
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffNo stamp cost set on LXM to Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3destination_hashTb4b4b4)Tffd700}Ta5d6ff, autoconfigured to Tffd700{Te6edf3stamp_costTffd700}Ta5d6ff, as required by latest announceTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3lxmessageTff7b72.Td2a8ffstate Tff7b72= Te6edf3LXMessageTff7b72.Td2a8ffOUTBOUND
T8b949e# If an outbound ticket is available for this
T8b949e# destination, attach it to the message.
Te6edf3lxmessageTff7b72.Td2a8ffoutbound_ticket Tff7b72= Tff7b72selfTff7b72.Td2a8ffget_outbound_ticketTb4b4b4(Te6edf3destination_hashTb4b4b4)
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8ffoutbound_ticket Tff7b72!= Tff7b72None Tff7b72and Te6edf3lxmessageTff7b72.Td2a8ffdefer_stampTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffDeferred stamp generation was requested for Tffd700{Te6edf3lxmessageTffd700}Ta5d6ff, but outbound ticket was applied, processing immediatelyTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3lxmessageTff7b72.Td2a8ffdefer_stamp Tff7b72= Tff7b72False
T8b949e# If requested, include a ticket to allow the
T8b949e# destination to reply without generating a stamp.
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8ffinclude_ticketTb4b4b4:
Te6edf3ticket Tff7b72= Tff7b72selfTff7b72.Td2a8ffgenerate_ticketTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffdestination_hashTb4b4b4)
Tff7b72if Te6edf3ticketTb4b4b4: Te6edf3lxmessageTff7b72.Td2a8fffieldsTb4b4b4[Te6edf3FIELD_TICKETTb4b4b4] Tff7b72= Te6edf3ticket
Tff7b72if Tff7b72not Te6edf3lxmessageTff7b72.Td2a8ffpackedTb4b4b4: Te6edf3lxmessageTff7b72.Td2a8ffpackTb4b4b4(Tb4b4b4)
Te6edf3unknown_path_requested Tff7b72= Tff7b72False
Tff7b72if Tff7b72not Te6edf3RNSTff7b72.Td2a8ffTransportTff7b72.Td2a8ffhas_pathTb4b4b4(Te6edf3destination_hashTb4b4b4) Tff7b72and Te6edf3lxmessageTff7b72.Td2a8ffmethod Tff7b72== Te6edf3LXMessageTff7b72.Td2a8ffOPPORTUNISTICTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffPre-emptively requesting unknown path for opportunistic Tffd700{Te6edf3lxmessageTffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3RNSTff7b72.Td2a8ffTransportTff7b72.Td2a8ffrequest_pathTb4b4b4(Te6edf3destination_hashTb4b4b4)
Te6edf3lxmessageTff7b72.Td2a8ffnext_delivery_attempt Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72+ Te6edf3LXMRouterTff7b72.Td2a8ffPATH_REQUEST_WAIT
Te6edf3unknown_path_requested Tff7b72= Tff7b72True
Te6edf3lxmessageTff7b72.Td2a8ffdetermine_transport_encryptionTb4b4b4(Tb4b4b4)
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8ffdefer_stamp Tff7b72and Te6edf3lxmessageTff7b72.Td2a8ffstamp_cost Tff7b72== Tff7b72NoneTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffDeferred stamp generation was requested for Tffd700{Te6edf3lxmessageTffd700}Ta5d6ff, but no stamp is required, processing immediatelyTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3lxmessageTff7b72.Td2a8ffdefer_stamp Tff7b72= Tff7b72False
Tff7b72if Tff7b72not Te6edf3lxmessageTff7b72.Td2a8ffdefer_stamp Tff7b72and Tff7b72not Tb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffdesired_method Tff7b72== Te6edf3LXMessageTff7b72.Td2a8ffPROPAGATED Tff7b72and Te6edf3lxmessageTff7b72.Td2a8ffdefer_propagation_stampTb4b4b4)Tb4b4b4:
Tff7b72while Tff7b72not Te6edf3unknown_path_requested Tff7b72and Tff7b72selfTff7b72.Td2a8ffprocessing_outboundTb4b4b4: Te6edf3timeTff7b72.Td2a8ffsleepTb4b4b4(T79c0ff0.05Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpending_outboundTff7b72.Td2a8ffappendTb4b4b4(Te6edf3lxmessageTb4b4b4)
Tff7b72if Tff7b72not Te6edf3unknown_path_requestedTb4b4b4: Tff7b72selfTff7b72.Td2a8ffprocess_outboundTb4b4b4(Tb4b4b4)
Tff7b72elseTb4b4b4: Tff7b72selfTff7b72.Td2a8ffpending_deferred_stampsTb4b4b4[Te6edf3lxmessageTff7b72.Td2a8ffmessage_idTb4b4b4] Tff7b72= Te6edf3lxmessage
Tff7b72def Td2a8ffget_outbound_progressTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3lxm_hashTb4b4b4)Tb4b4b4:
Tff7b72for Te6edf3lxm Tff7b72in Tff7b72selfTff7b72.Td2a8ffpending_outboundTb4b4b4:
Tff7b72if Te6edf3lxmTff7b72.Td2a8ffhash Tff7b72== Te6edf3lxm_hashTb4b4b4:
Tff7b72return Te6edf3lxmTff7b72.Td2a8ffprogress
Tff7b72for Te6edf3lxm_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffpending_deferred_stampsTb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8ffpending_deferred_stampsTb4b4b4[Te6edf3lxm_idTb4b4b4]Tff7b72.Td2a8ffhash Tff7b72== Te6edf3lxm_hashTb4b4b4:
Tff7b72return Tff7b72selfTff7b72.Td2a8ffpending_deferred_stampsTb4b4b4[Te6edf3lxm_idTb4b4b4]Tff7b72.Td2a8ffprogress
Tff7b72return Tff7b72None
Tff7b72def Td2a8ffget_outbound_lxm_stamp_costTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3lxm_hashTb4b4b4)Tb4b4b4:
Tff7b72for Te6edf3lxm Tff7b72in Tff7b72selfTff7b72.Td2a8ffpending_outboundTb4b4b4:
Tff7b72if Te6edf3lxmTff7b72.Td2a8ffhash Tff7b72== Te6edf3lxm_hashTb4b4b4:
Tff7b72if Te6edf3lxmTff7b72.Td2a8ffoutbound_ticketTb4b4b4: Tff7b72return Tff7b72None
Tff7b72elseTb4b4b4: Tff7b72return Te6edf3lxmTff7b72.Td2a8ffstamp_cost
Tff7b72for Te6edf3lxm_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffpending_deferred_stampsTb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8ffpending_deferred_stampsTb4b4b4[Te6edf3lxm_idTb4b4b4]Tff7b72.Td2a8ffhash Tff7b72== Te6edf3lxm_hashTb4b4b4:
Te6edf3lxm Tff7b72= Tff7b72selfTff7b72.Td2a8ffpending_deferred_stampsTb4b4b4[Te6edf3lxm_idTb4b4b4]
Tff7b72if Te6edf3lxmTff7b72.Td2a8ffoutbound_ticketTb4b4b4: Tff7b72return Tff7b72None
Tff7b72elseTb4b4b4: Tff7b72return Te6edf3lxmTff7b72.Td2a8ffstamp_cost
Tff7b72return Tff7b72None
Tff7b72def Td2a8ffget_outbound_lxm_propagation_stamp_costTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3lxm_hashTb4b4b4)Tb4b4b4:
Tff7b72for Te6edf3lxm Tff7b72in Tff7b72selfTff7b72.Td2a8ffpending_outboundTb4b4b4:
Tff7b72if Te6edf3lxmTff7b72.Td2a8ffhash Tff7b72== Te6edf3lxm_hashTb4b4b4:
Tff7b72return Te6edf3lxmTff7b72.Td2a8ffpropagation_target_cost
Tff7b72for Te6edf3lxm_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffpending_deferred_stampsTb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8ffpending_deferred_stampsTb4b4b4[Te6edf3lxm_idTb4b4b4]Tff7b72.Td2a8ffhash Tff7b72== Te6edf3lxm_hashTb4b4b4:
Tff7b72return Tff7b72selfTff7b72.Td2a8ffpending_deferred_stampsTb4b4b4[Te6edf3lxm_idTb4b4b4]Tff7b72.Td2a8ffpropagation_target_cost
Tff7b72return Tff7b72None
T8b949e### Message Routing & Delivery ########################
T8b949e#######################################################
Tff7b72def Td2a8fflxmf_deliveryTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3lxmf_dataTb4b4b4, Te6edf3destination_type Tff7b72= Tff7b72NoneTb4b4b4, Te6edf3phy_stats Tff7b72= Tff7b72NoneTb4b4b4, Te6edf3ratchet_id Tff7b72= Tff7b72NoneTb4b4b4, Te6edf3method Tff7b72= Tff7b72NoneTb4b4b4, Te6edf3no_stamp_enforcementTff7b72=Tff7b72FalseTb4b4b4, Te6edf3allow_duplicateTff7b72=Tff7b72FalseTb4b4b4)Tb4b4b4:
Tff7b72tryTb4b4b4:
Te6edf3message Tff7b72= Te6edf3LXMessageTff7b72.Td2a8ffunpack_from_bytesTb4b4b4(Te6edf3lxmf_dataTb4b4b4)
Tff7b72if Te6edf3ratchet_id Tff7b72and Tff7b72not Te6edf3messageTff7b72.Td2a8ffratchet_idTb4b4b4:
Te6edf3messageTff7b72.Td2a8ffratchet_id Tff7b72= Te6edf3ratchet_id
Tff7b72if Te6edf3methodTb4b4b4:
Te6edf3messageTff7b72.Td2a8ffmethod Tff7b72= Te6edf3method
Tff7b72if Te6edf3messageTff7b72.Td2a8ffsignature_validated Tff7b72and Te6edf3FIELD_TICKET Tff7b72in Te6edf3messageTff7b72.Td2a8fffieldsTb4b4b4:
Te6edf3ticket_entry Tff7b72= Te6edf3messageTff7b72.Td2a8fffieldsTb4b4b4[Te6edf3FIELD_TICKETTb4b4b4]
Tff7b72if Tffa657typeTb4b4b4(Te6edf3ticket_entryTb4b4b4) Tff7b72== Tffa657list Tff7b72and Tffa657lenTb4b4b4(Te6edf3ticket_entryTb4b4b4) Tff7b72> T79c0ff1Tb4b4b4:
Te6edf3expires Tff7b72= Te6edf3ticket_entryTb4b4b4[T79c0ff0Tb4b4b4]
Te6edf3ticket Tff7b72= Te6edf3ticket_entryTb4b4b4[T79c0ff1Tb4b4b4]
Tff7b72if Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72< Te6edf3expiresTb4b4b4:
Tff7b72if Tffa657typeTb4b4b4(Te6edf3ticketTb4b4b4) Tff7b72== Tffa657bytes Tff7b72and Tffa657lenTb4b4b4(Te6edf3ticketTb4b4b4) Tff7b72== Te6edf3LXMessageTff7b72.Td2a8ffTICKET_LENGTHTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffremember_ticketTb4b4b4(Te6edf3messageTff7b72.Td2a8ffsource_hashTb4b4b4, Te6edf3ticket_entryTb4b4b4)
Tff7b72def Td2a8ffsave_jobTb4b4b4(Tb4b4b4)Tb4b4b4:
Tff7b72selfTff7b72.Td2a8ffsave_available_ticketsTb4b4b4(Tb4b4b4)
Te6edf3threadingTff7b72.Td2a8ffThreadTb4b4b4(Te6edf3targetTff7b72=Te6edf3save_jobTb4b4b4, Te6edf3daemonTff7b72=Tff7b72TrueTb4b4b4)Tff7b72.Td2a8ffstartTb4b4b4(Tb4b4b4)
Te6edf3required_stamp_cost Tff7b72= Tff7b72selfTff7b72.Td2a8ffdelivery_destinationsTb4b4b4[Te6edf3messageTff7b72.Td2a8ffdestination_hashTb4b4b4]Tff7b72.Td2a8ffstamp_cost
Tff7b72if Te6edf3required_stamp_cost Tff7b72!= Tff7b72NoneTb4b4b4:
Te6edf3destination_tickets Tff7b72= Tff7b72selfTff7b72.Td2a8ffget_inbound_ticketsTb4b4b4(Te6edf3messageTff7b72.Td2a8ffsource_hashTb4b4b4)
Tff7b72if Te6edf3messageTff7b72.Td2a8ffvalidate_stampTb4b4b4(Te6edf3required_stamp_costTb4b4b4, Te6edf3ticketsTff7b72=Te6edf3destination_ticketsTb4b4b4)Tb4b4b4:
Te6edf3messageTff7b72.Td2a8ffstamp_valid Tff7b72= Tff7b72True
Te6edf3messageTff7b72.Td2a8ffstamp_checked Tff7b72= Tff7b72True
Tff7b72elseTb4b4b4:
Te6edf3messageTff7b72.Td2a8ffstamp_valid Tff7b72= Tff7b72False
Te6edf3messageTff7b72.Td2a8ffstamp_checked Tff7b72= Tff7b72True
Tff7b72if Tff7b72not Te6edf3messageTff7b72.Td2a8ffstamp_validTb4b4b4:
Tff7b72if Te6edf3no_stamp_enforcementTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffReceived Tffd700{Te6edf3messageTffd700}Ta5d6ff with invalid stamp, but allowing anyway, since stamp enforcement was temporarily disabledTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_NOTICETb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8ff_enforce_stampsTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffDropping Tffd700{Te6edf3messageTffd700}Ta5d6ff with invalid stampTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_NOTICETb4b4b4)
Tff7b72return Tff7b72False
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffReceived Tffd700{Te6edf3messageTffd700}Ta5d6ff with invalid stamp, but allowing anyway, since stamp enforcement is disabledTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_NOTICETb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffReceived Tffd700{Te6edf3messageTffd700}Ta5d6ff with valid stampTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72if Te6edf3phy_stats Tff7b72!= Tff7b72NoneTb4b4b4:
Tff7b72if Ta5d6ff"Ta5d6ffrssiTa5d6ff" Tff7b72in Te6edf3phy_statsTb4b4b4: Te6edf3messageTff7b72.Td2a8ffrssi Tff7b72= Te6edf3phy_statsTb4b4b4[Ta5d6ff"Ta5d6ffrssiTa5d6ff"Tb4b4b4]
Tff7b72if Ta5d6ff"Ta5d6ffsnrTa5d6ff" Tff7b72in Te6edf3phy_statsTb4b4b4: Te6edf3messageTff7b72.Td2a8ffsnr Tff7b72= Te6edf3phy_statsTb4b4b4[Ta5d6ff"Ta5d6ffsnrTa5d6ff"Tb4b4b4]
Tff7b72if Ta5d6ff"Ta5d6ffqTa5d6ff" Tff7b72in Te6edf3phy_statsTb4b4b4: Te6edf3messageTff7b72.Td2a8ffq Tff7b72= Te6edf3phy_statsTb4b4b4[Ta5d6ff"Ta5d6ffqTa5d6ff"Tb4b4b4]
T8b949e# TODO: Update these descriptions to account for ratchets
Tff7b72if Te6edf3destination_type Tff7b72== Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffSINGLETb4b4b4:
Te6edf3messageTff7b72.Td2a8fftransport_encrypted Tff7b72= Tff7b72True
Te6edf3messageTff7b72.Td2a8fftransport_encryption Tff7b72= Te6edf3LXMessageTff7b72.Td2a8ffENCRYPTION_DESCRIPTION_EC
Tff7b72elif Te6edf3destination_type Tff7b72== Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffGROUPTb4b4b4:
Te6edf3messageTff7b72.Td2a8fftransport_encrypted Tff7b72= Tff7b72True
Te6edf3messageTff7b72.Td2a8fftransport_encryption Tff7b72= Te6edf3LXMessageTff7b72.Td2a8ffENCRYPTION_DESCRIPTION_AES
Tff7b72elif Te6edf3destination_type Tff7b72== Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffLINKTb4b4b4:
Te6edf3messageTff7b72.Td2a8fftransport_encrypted Tff7b72= Tff7b72True
Te6edf3messageTff7b72.Td2a8fftransport_encryption Tff7b72= Te6edf3LXMessageTff7b72.Td2a8ffENCRYPTION_DESCRIPTION_EC
Tff7b72elseTb4b4b4:
Te6edf3messageTff7b72.Td2a8fftransport_encrypted Tff7b72= Tff7b72False
Te6edf3messageTff7b72.Td2a8fftransport_encryption Tff7b72= Tff7b72None
Tff7b72if Te6edf3messageTff7b72.Td2a8ffsource_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffignored_listTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Tffa657strTb4b4b4(Tff7b72selfTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff ignored message from Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3messageTff7b72.Td2a8ffsource_hashTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72return Tff7b72False
Tff7b72if Tff7b72not Te6edf3allow_duplicate Tff7b72and Tff7b72selfTff7b72.Td2a8ffhas_messageTb4b4b4(Te6edf3messageTff7b72.Td2a8ffhashTb4b4b4)Tb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Tffa657strTb4b4b4(Tff7b72selfTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff ignored already received message from Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3messageTff7b72.Td2a8ffsource_hashTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72return Tff7b72False
Tff7b72elseTb4b4b4:
Tff7b72selfTff7b72.Td2a8fflocally_delivered_transient_idsTb4b4b4[Te6edf3messageTff7b72.Td2a8ffhashTb4b4b4] Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)
Tff7b72if Tff7b72selfTff7b72.Td2a8ff__delivery_callback Tff7b72!= Tff7b72None Tff7b72and Tffa657callableTb4b4b4(Tff7b72selfTff7b72.Td2a8ff__delivery_callbackTb4b4b4)Tb4b4b4:
Tff7b72tryTb4b4b4:
Tff7b72selfTff7b72.Td2a8ff__delivery_callbackTb4b4b4(Te6edf3messageTb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffAn error occurred in the external delivery callback for Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3messageTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Te6edf3RNSTff7b72.Td2a8fftrace_exceptionTb4b4b4(Te6edf3eTb4b4b4)
Tff7b72return Tff7b72True
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCould not assemble LXMF message from received dataTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_NOTICETb4b4b4)
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffThe contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72return Tff7b72False
Tff7b72def Td2a8ffdelivery_packetTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3dataTb4b4b4, Te6edf3packetTb4b4b4)Tb4b4b4:
Te6edf3packetTff7b72.Td2a8ffproveTb4b4b4(Tb4b4b4)
Tff7b72tryTb4b4b4:
Te6edf3method Tff7b72= Tff7b72None
Tff7b72if Te6edf3packetTff7b72.Td2a8ffdestination_type Tff7b72!= Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffLINKTb4b4b4:
Te6edf3method Tff7b72= Te6edf3LXMessageTff7b72.Td2a8ffOPPORTUNISTIC
Te6edf3lxmf_data Tff7b72= Ta5d6ffbTa5d6ff"Ta5d6ff"
Te6edf3lxmf_data Tff7b72+Tff7b72= Te6edf3packetTff7b72.Td2a8ffdestinationTff7b72.Td2a8ffhash
Te6edf3lxmf_data Tff7b72+Tff7b72= Te6edf3data
Tff7b72elseTb4b4b4:
Te6edf3method Tff7b72= Te6edf3LXMessageTff7b72.Td2a8ffDIRECT
Te6edf3lxmf_data Tff7b72= Te6edf3data
Tff7b72tryTb4b4b4:
Te6edf3reticulum Tff7b72= Te6edf3RNSTff7b72.Td2a8ffReticulumTff7b72.Td2a8ffget_instanceTb4b4b4(Tb4b4b4)
Tff7b72if Te6edf3packetTff7b72.Td2a8ffrssi Tff7b72== Tff7b72NoneTb4b4b4: Te6edf3packetTff7b72.Td2a8ffrssi Tff7b72= Te6edf3reticulumTff7b72.Td2a8ffget_packet_rssiTb4b4b4(Te6edf3packetTff7b72.Td2a8ffpacket_hashTb4b4b4)
Tff7b72if Te6edf3packetTff7b72.Td2a8ffsnr Tff7b72== Tff7b72NoneTb4b4b4: Te6edf3packetTff7b72.Td2a8ffsnr Tff7b72= Te6edf3reticulumTff7b72.Td2a8ffget_packet_snrTb4b4b4(Te6edf3packetTff7b72.Td2a8ffpacket_hashTb4b4b4)
Tff7b72if Te6edf3packetTff7b72.Td2a8ffq Tff7b72== Tff7b72NoneTb4b4b4: Te6edf3packetTff7b72.Td2a8ffq Tff7b72= Te6edf3reticulumTff7b72.Td2a8ffget_packet_qTb4b4b4(Te6edf3packetTff7b72.Td2a8ffpacket_hashTb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffError while retrieving physical link stats for LXMF delivery packet: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Te6edf3phy_stats Tff7b72= Tb4b4b4{Ta5d6ff"Ta5d6ffrssiTa5d6ff"Tb4b4b4: Te6edf3packetTff7b72.Td2a8ffrssiTb4b4b4, Ta5d6ff"Ta5d6ffsnrTa5d6ff"Tb4b4b4: Te6edf3packetTff7b72.Td2a8ffsnrTb4b4b4, Ta5d6ff"Ta5d6ffqTa5d6ff"Tb4b4b4: Te6edf3packetTff7b72.Td2a8ffqTb4b4b4}
Tff7b72selfTff7b72.Td2a8fflxmf_deliveryTb4b4b4(Te6edf3lxmf_dataTb4b4b4, Te6edf3packetTff7b72.Td2a8ffdestination_typeTb4b4b4, Te6edf3phy_statsTff7b72=Te6edf3phy_statsTb4b4b4, Te6edf3ratchet_idTff7b72=Te6edf3packetTff7b72.Td2a8ffratchet_idTb4b4b4, Te6edf3methodTff7b72=Te6edf3methodTb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffException occurred while parsing incoming LXMF data.Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffThe contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72def Td2a8ffdelivery_link_establishedTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3linkTb4b4b4)Tb4b4b4:
Te6edf3linkTff7b72.Td2a8fftrack_phy_statsTb4b4b4(Tff7b72TrueTb4b4b4)
Te6edf3linkTff7b72.Td2a8ffset_packet_callbackTb4b4b4(Tff7b72selfTff7b72.Td2a8ffdelivery_packetTb4b4b4)
Te6edf3linkTff7b72.Td2a8ffset_resource_strategyTb4b4b4(Te6edf3RNSTff7b72.Td2a8ffLinkTff7b72.Td2a8ffACCEPT_APPTb4b4b4)
Te6edf3linkTff7b72.Td2a8ffset_resource_callbackTb4b4b4(Tff7b72selfTff7b72.Td2a8ffdelivery_resource_advertisedTb4b4b4)
Te6edf3linkTff7b72.Td2a8ffset_resource_started_callbackTb4b4b4(Tff7b72selfTff7b72.Td2a8ffresource_transfer_beganTb4b4b4)
Te6edf3linkTff7b72.Td2a8ffset_resource_concluded_callbackTb4b4b4(Tff7b72selfTff7b72.Td2a8ffdelivery_resource_concludedTb4b4b4)
Te6edf3linkTff7b72.Td2a8ffset_remote_identified_callbackTb4b4b4(Tff7b72selfTff7b72.Td2a8ffdelivery_remote_identifiedTb4b4b4)
Tff7b72def Td2a8ffdelivery_link_closedTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3linkTb4b4b4)Tb4b4b4:
Tff7b72pass
Tff7b72def Td2a8ffresource_transfer_beganTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3resourceTb4b4b4)Tb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffTransfer began for LXMF delivery resource Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3resourceTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72def Td2a8ffdelivery_resource_advertisedTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3resourceTb4b4b4)Tb4b4b4:
Te6edf3size Tff7b72= Te6edf3resourceTff7b72.Td2a8ffget_data_sizeTb4b4b4(Tb4b4b4)
Te6edf3limit Tff7b72= Tff7b72selfTff7b72.Td2a8ffdelivery_per_transfer_limitTff7b72*T79c0ff1000
Tff7b72if Te6edf3limit Tff7b72!= Tff7b72None Tff7b72and Te6edf3size Tff7b72> Te6edf3limitTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffRejecting Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettysizeTb4b4b4(Te6edf3sizeTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff incoming LXMF delivery resource, since it exceeds the limit of Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettysizeTb4b4b4(Te6edf3limitTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72return Tff7b72False
Tff7b72elseTb4b4b4:
Tff7b72return Tff7b72True
Tff7b72def Td2a8ffdelivery_resource_concludedTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3resourceTb4b4b4)Tb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffTransfer concluded for LXMF delivery resource Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3resourceTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72if Te6edf3resourceTff7b72.Td2a8ffstatus Tff7b72== Te6edf3RNSTff7b72.Td2a8ffResourceTff7b72.Td2a8ffCOMPLETETb4b4b4:
Te6edf3ratchet_id Tff7b72= Tff7b72None
T8b949e# Set ratchet ID to link ID if available
Tff7b72if Te6edf3resourceTff7b72.Td2a8fflink Tff7b72and Tffa657hasattrTb4b4b4(Te6edf3resourceTff7b72.Td2a8fflinkTb4b4b4, Ta5d6ff"Ta5d6fflink_idTa5d6ff"Tb4b4b4)Tb4b4b4:
Te6edf3ratchet_id Tff7b72= Te6edf3resourceTff7b72.Td2a8fflinkTff7b72.Td2a8fflink_id
Te6edf3phy_stats Tff7b72= Tb4b4b4{Ta5d6ff"Ta5d6ffrssiTa5d6ff"Tb4b4b4: Te6edf3resourceTff7b72.Td2a8fflinkTff7b72.Td2a8ffrssiTb4b4b4, Ta5d6ff"Ta5d6ffsnrTa5d6ff"Tb4b4b4: Te6edf3resourceTff7b72.Td2a8fflinkTff7b72.Td2a8ffsnrTb4b4b4, Ta5d6ff"Ta5d6ffqTa5d6ff"Tb4b4b4: Te6edf3resourceTff7b72.Td2a8fflinkTff7b72.Td2a8ffqTb4b4b4}
Tff7b72selfTff7b72.Td2a8fflxmf_deliveryTb4b4b4(Te6edf3resourceTff7b72.Td2a8ffdataTff7b72.Td2a8ffreadTb4b4b4(Tb4b4b4)Tb4b4b4, Te6edf3resourceTff7b72.Td2a8fflinkTff7b72.Td2a8fftypeTb4b4b4, Te6edf3phy_statsTff7b72=Te6edf3phy_statsTb4b4b4, Te6edf3ratchet_idTff7b72=Te6edf3ratchet_idTb4b4b4, Te6edf3methodTff7b72=Te6edf3LXMessageTff7b72.Td2a8ffDIRECTTb4b4b4)
Tff7b72def Td2a8ffdelivery_remote_identifiedTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3linkTb4b4b4, Te6edf3identityTb4b4b4)Tb4b4b4:
Te6edf3destination_hash Tff7b72= Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffhash_from_name_and_identityTb4b4b4(Ta5d6ff"Ta5d6fflxmf.deliveryTa5d6ff"Tb4b4b4, Te6edf3identityTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffbackchannel_linksTb4b4b4[Te6edf3destination_hashTb4b4b4] Tff7b72= Te6edf3link
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffBackchannel became available for Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3destination_hashTb4b4b4)Tffd700}Ta5d6ff on delivery link Tffd700{Te6edf3linkTffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
T8b949e### Peer Sync & Propagation ###########################
T8b949e#######################################################
Tff7b72def Td2a8ffpeerTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3destination_hashTb4b4b4, Te6edf3timestampTb4b4b4, Te6edf3propagation_transfer_limitTb4b4b4, Te6edf3propagation_sync_limitTb4b4b4, Te6edf3propagation_stamp_costTb4b4b4, Te6edf3propagation_stamp_cost_flexibilityTb4b4b4, Te6edf3peering_costTb4b4b4, Te6edf3metadataTb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3peering_cost Tff7b72> Tff7b72selfTff7b72.Td2a8ffmax_peering_costTb4b4b4:
Tff7b72if Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffPeer Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3destination_hashTb4b4b4)Tffd700}Ta5d6ff increased peering cost beyond local accepted maximum, breaking peering...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_NOTICETb4b4b4)
Tff7b72selfTff7b72.Td2a8ffunpeerTb4b4b4(Te6edf3destination_hashTb4b4b4, Te6edf3timestampTb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffNot peering with Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3destination_hashTb4b4b4)Tffd700}Ta5d6ff, since its peering cost of Tffd700{Te6edf3peering_costTffd700}Ta5d6ff exceeds local maximum of Tffd700{Tff7b72selfTff7b72.Td2a8ffmax_peering_costTffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_NOTICETb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72if Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4:
Te6edf3peer Tff7b72= Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4[Te6edf3destination_hashTb4b4b4]
Tff7b72if Te6edf3timestamp Tff7b72> Te6edf3peerTff7b72.Td2a8ffpeering_timebaseTb4b4b4:
Te6edf3peerTff7b72.Td2a8ffalive Tff7b72= Tff7b72True
Te6edf3peerTff7b72.Td2a8ffmetadata Tff7b72= Te6edf3metadata
Te6edf3peerTff7b72.Td2a8ffsync_backoff Tff7b72= T79c0ff0
Te6edf3peerTff7b72.Td2a8ffnext_sync_attempt Tff7b72= T79c0ff0
Te6edf3peerTff7b72.Td2a8ffpeering_timebase Tff7b72= Te6edf3timestamp
Te6edf3peerTff7b72.Td2a8fflast_heard Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)
Te6edf3peerTff7b72.Td2a8ffpropagation_stamp_cost Tff7b72= Te6edf3propagation_stamp_cost
Te6edf3peerTff7b72.Td2a8ffpropagation_stamp_cost_flexibility Tff7b72= Te6edf3propagation_stamp_cost_flexibility
Te6edf3peerTff7b72.Td2a8ffpeering_cost Tff7b72= Te6edf3peering_cost
Te6edf3peerTff7b72.Td2a8ffpropagation_transfer_limit Tff7b72= Te6edf3propagation_transfer_limit
Tff7b72if Te6edf3propagation_sync_limit Tff7b72!= Tff7b72NoneTb4b4b4: Te6edf3peerTff7b72.Td2a8ffpropagation_sync_limit Tff7b72= Te6edf3propagation_sync_limit
Tff7b72elseTb4b4b4: Te6edf3peerTff7b72.Td2a8ffpropagation_sync_limit Tff7b72= Te6edf3propagation_transfer_limit
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffPeering config updated for Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3destination_hashTb4b4b4)Tffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_VERBOSETb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72if Tffa657lenTb4b4b4(Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4) Tff7b72>Tff7b72= Tff7b72selfTff7b72.Td2a8ffmax_peersTb4b4b4: Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffMax peers reached, not peering with Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3destination_hashTb4b4b4)Tffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3peer Tff7b72= Te6edf3LXMPeerTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3destination_hashTb4b4b4, Te6edf3sync_strategyTff7b72=Tff7b72selfTff7b72.Td2a8ffdefault_sync_strategyTb4b4b4)
Te6edf3peerTff7b72.Td2a8ffalive Tff7b72= Tff7b72True
Te6edf3peerTff7b72.Td2a8ffmetadata Tff7b72= Te6edf3metadata
Te6edf3peerTff7b72.Td2a8fflast_heard Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)
Te6edf3peerTff7b72.Td2a8ffpropagation_stamp_cost Tff7b72= Te6edf3propagation_stamp_cost
Te6edf3peerTff7b72.Td2a8ffpropagation_stamp_cost_flexibility Tff7b72= Te6edf3propagation_stamp_cost_flexibility
Te6edf3peerTff7b72.Td2a8ffpeering_cost Tff7b72= Te6edf3peering_cost
Te6edf3peerTff7b72.Td2a8ffpropagation_transfer_limit Tff7b72= Te6edf3propagation_transfer_limit
Tff7b72if Te6edf3propagation_sync_limit Tff7b72!= Tff7b72NoneTb4b4b4: Te6edf3peerTff7b72.Td2a8ffpropagation_sync_limit Tff7b72= Te6edf3propagation_sync_limit
Tff7b72elseTb4b4b4: Te6edf3peerTff7b72.Td2a8ffpropagation_sync_limit Tff7b72= Te6edf3propagation_transfer_limit
Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4[Te6edf3destination_hashTb4b4b4] Tff7b72= Te6edf3peer
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffPeered with Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3destination_hashTb4b4b4)Tffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_NOTICETb4b4b4)
Tff7b72def Td2a8ffunpeerTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3destination_hashTb4b4b4, Te6edf3timestamp Tff7b72= Tff7b72NoneTb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3timestamp Tff7b72== Tff7b72NoneTb4b4b4:
Te6edf3timestamp Tff7b72= Tffa657intTb4b4b4(Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)Tb4b4b4)
Tff7b72if Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4:
Te6edf3peer Tff7b72= Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4[Te6edf3destination_hashTb4b4b4]
Tff7b72if Te6edf3timestamp Tff7b72>Tff7b72= Te6edf3peerTff7b72.Td2a8ffpeering_timebaseTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffpeersTff7b72.Td2a8ffpopTb4b4b4(Te6edf3destination_hashTb4b4b4)
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffBroke peering with Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3peerTff7b72.Td2a8ffdestinationTb4b4b4)Tb4b4b4)
Tff7b72def Td2a8ffrotate_peersTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72tryTb4b4b4:
Te6edf3rotation_headroom Tff7b72= Tffa657maxTb4b4b4(T79c0ff1Tb4b4b4, Te6edf3mathTff7b72.Td2a8fffloorTb4b4b4(Tff7b72selfTff7b72.Td2a8ffmax_peersTff7b72*Tb4b4b4(Te6edf3LXMRouterTff7b72.Td2a8ffROTATION_HEADROOM_PCTTff7b72/T79c0ff100.0Tb4b4b4)Tb4b4b4)Tb4b4b4)
Te6edf3required_drops Tff7b72= Tffa657lenTb4b4b4(Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4) Tff7b72- Tb4b4b4(Tff7b72selfTff7b72.Td2a8ffmax_peers Tff7b72- Te6edf3rotation_headroomTb4b4b4)
Tff7b72if Te6edf3required_drops Tff7b72> T79c0ff0 Tff7b72and Tffa657lenTb4b4b4(Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4) Tff7b72- Te6edf3required_drops Tff7b72> T79c0ff1Tb4b4b4:
Te6edf3peers Tff7b72= Tff7b72selfTff7b72.Td2a8ffpeersTff7b72.Td2a8ffcopyTb4b4b4(Tb4b4b4)
Te6edf3untested_peers Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72for Te6edf3peer_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4:
Te6edf3peer Tff7b72= Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4[Te6edf3peer_idTb4b4b4]
Tff7b72if Te6edf3peerTff7b72.Td2a8fflast_sync_attempt Tff7b72== T79c0ff0Tb4b4b4:
Te6edf3untested_peersTff7b72.Td2a8ffappendTb4b4b4(Te6edf3peerTb4b4b4)
Tff7b72if Tffa657lenTb4b4b4(Te6edf3untested_peersTb4b4b4) Tff7b72>Tff7b72= Te6edf3rotation_headroomTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffNewly added peer threshold reached, postponing peer rotationTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72return
Te6edf3fully_synced_peers Tff7b72= Tb4b4b4{Tb4b4b4}
Tff7b72for Te6edf3peer_id Tff7b72in Te6edf3peersTb4b4b4:
Te6edf3peer Tff7b72= Te6edf3peersTb4b4b4[Te6edf3peer_idTb4b4b4]
Tff7b72if Te6edf3peerTff7b72.Td2a8ffunhandled_message_count Tff7b72== T79c0ff0Tb4b4b4:
Te6edf3fully_synced_peersTb4b4b4[Te6edf3peer_idTb4b4b4] Tff7b72= Te6edf3peer
Tff7b72if Tffa657lenTb4b4b4(Te6edf3fully_synced_peersTb4b4b4) Tff7b72> T79c0ff0Tb4b4b4:
Te6edf3peers Tff7b72= Te6edf3fully_synced_peers
Te6edf3ms Tff7b72= Ta5d6ff"Ta5d6ff" Tff7b72if Tffa657lenTb4b4b4(Te6edf3fully_synced_peersTb4b4b4) Tff7b72== T79c0ff1 Tff7b72else Ta5d6ff"Ta5d6ffsTa5d6ff"
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffFound Tffd700{Tffa657lenTb4b4b4(Te6edf3fully_synced_peersTb4b4b4)Tffd700}Ta5d6ff fully synced peerTffd700{Te6edf3msTffd700}Ta5d6ff, using as peer rotation pool basisTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3culled_peers Tff7b72= Tb4b4b4[Tb4b4b4]
Te6edf3waiting_peers Tff7b72= Tb4b4b4[Tb4b4b4]
Te6edf3unresponsive_peers Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72for Te6edf3peer_id Tff7b72in Te6edf3peersTb4b4b4:
Te6edf3peer Tff7b72= Te6edf3peersTb4b4b4[Te6edf3peer_idTb4b4b4]
Tff7b72if Tff7b72not Te6edf3peer_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffstatic_peers Tff7b72and Te6edf3peerTff7b72.Td2a8ffstate Tff7b72== Te6edf3LXMPeerTff7b72.Td2a8ffIDLETb4b4b4:
Tff7b72if Te6edf3peerTff7b72.Td2a8ffaliveTb4b4b4:
Tff7b72if Te6edf3peerTff7b72.Td2a8ffoffered Tff7b72== T79c0ff0Tb4b4b4:
T8b949e# Don't consider for unpeering until at
T8b949e# least one message has been offered
Tff7b72pass
Tff7b72elseTb4b4b4:
Te6edf3waiting_peersTff7b72.Td2a8ffappendTb4b4b4(Te6edf3peerTb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3unresponsive_peersTff7b72.Td2a8ffappendTb4b4b4(Te6edf3peerTb4b4b4)
Te6edf3drop_pool Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72if Tffa657lenTb4b4b4(Te6edf3unresponsive_peersTb4b4b4) Tff7b72> T79c0ff0Tb4b4b4:
Te6edf3drop_poolTff7b72.Td2a8ffextendTb4b4b4(Te6edf3unresponsive_peersTb4b4b4)
Tff7b72if Tff7b72not Tff7b72selfTff7b72.Td2a8ffprioritise_rotating_unreachable_peersTb4b4b4:
Te6edf3drop_poolTff7b72.Td2a8ffextendTb4b4b4(Te6edf3waiting_peersTb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3drop_poolTff7b72.Td2a8ffextendTb4b4b4(Te6edf3waiting_peersTb4b4b4)
Tff7b72if Tffa657lenTb4b4b4(Te6edf3drop_poolTb4b4b4) Tff7b72> T79c0ff0Tb4b4b4:
Te6edf3drop_count Tff7b72= Tffa657minTb4b4b4(Te6edf3required_dropsTb4b4b4, Tffa657lenTb4b4b4(Te6edf3drop_poolTb4b4b4)Tb4b4b4)
Te6edf3low_acceptance_rate_peers Tff7b72= Tffa657sortedTb4b4b4(
Te6edf3drop_poolTb4b4b4,
Te6edf3keyTff7b72=Tff7b72lambda Te6edf3pTb4b4b4: Tb4b4b4( T79c0ff0 Tff7b72if Te6edf3pTff7b72.Td2a8ffoffered Tff7b72== T79c0ff0 Tff7b72else Tb4b4b4(Te6edf3pTff7b72.Td2a8ffoutgoingTff7b72/Te6edf3pTff7b72.Td2a8ffofferedTb4b4b4) Tb4b4b4)Tb4b4b4,
Te6edf3reverseTff7b72=Tff7b72False
Tb4b4b4)Tb4b4b4[T79c0ff0Tb4b4b4:Te6edf3drop_countTb4b4b4]
Te6edf3dropped_peers Tff7b72= T79c0ff0
Tff7b72for Te6edf3peer Tff7b72in Te6edf3low_acceptance_rate_peersTb4b4b4:
Te6edf3ar Tff7b72= T79c0ff0 Tff7b72if Te6edf3peerTff7b72.Td2a8ffoffered Tff7b72== T79c0ff0 Tff7b72else Tffa657roundTb4b4b4(Tb4b4b4(Te6edf3peerTff7b72.Td2a8ffoutgoingTff7b72/Te6edf3peerTff7b72.Td2a8ffofferedTb4b4b4)Tff7b72*T79c0ff100Tb4b4b4, T79c0ff2Tb4b4b4)
Tff7b72if Te6edf3ar Tff7b72< Te6edf3LXMRouterTff7b72.Td2a8ffROTATION_AR_MAXTff7b72*T79c0ff100Tb4b4b4:
Te6edf3reachable_str Tff7b72= Ta5d6ff"Ta5d6ffreachableTa5d6ff" Tff7b72if Te6edf3peerTff7b72.Td2a8ffalive Tff7b72else Ta5d6ff"Ta5d6ffunreachableTa5d6ff"
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffAcceptance rate for Tffd700{Te6edf3reachable_strTffd700}Ta5d6ff peer Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3peerTff7b72.Td2a8ffdestination_hashTb4b4b4)Tffd700}Ta5d6ff was: Tffd700{Te6edf3arTffd700}Ta5d6ff% (Tffd700{Te6edf3peerTff7b72.Td2a8ffoutgoingTffd700}Ta5d6ff/Tffd700{Te6edf3peerTff7b72.Td2a8ffofferedTffd700}Ta5d6ff, Tffd700{Te6edf3peerTff7b72.Td2a8ffunhandled_message_countTffd700}Ta5d6ff unhandled messages)Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffunpeerTb4b4b4(Te6edf3peerTff7b72.Td2a8ffdestination_hashTb4b4b4)
Te6edf3dropped_peers Tff7b72+Tff7b72= T79c0ff1
Te6edf3ms Tff7b72= Ta5d6ff"Ta5d6ff" Tff7b72if Te6edf3dropped_peers Tff7b72== T79c0ff1 Tff7b72else Ta5d6ff"Ta5d6ffsTa5d6ff"
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffDropped Tffd700{Te6edf3dropped_peersTffd700}Ta5d6ff low acceptance rate peerTffd700{Te6edf3msTffd700}Ta5d6ff to increase peering headroomTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffAn error occurred during peer rotation: Tffd700{Te6edf3eTffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Te6edf3RNSTff7b72.Td2a8fftrace_exceptionTb4b4b4(Te6edf3eTb4b4b4)
Tff7b72def Td2a8ffsync_peersTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Te6edf3culled_peers Tff7b72= Tb4b4b4[Tb4b4b4]
Te6edf3waiting_peers Tff7b72= Tb4b4b4[Tb4b4b4]
Te6edf3unresponsive_peers Tff7b72= Tb4b4b4[Tb4b4b4]
Te6edf3peers Tff7b72= Tff7b72selfTff7b72.Td2a8ffpeersTff7b72.Td2a8ffcopyTb4b4b4(Tb4b4b4)
Tff7b72for Te6edf3peer_id Tff7b72in Te6edf3peersTb4b4b4:
Te6edf3peer Tff7b72= Te6edf3peersTb4b4b4[Te6edf3peer_idTb4b4b4]
Tff7b72if Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72> Te6edf3peerTff7b72.Td2a8fflast_heard Tff7b72+ Te6edf3LXMPeerTff7b72.Td2a8ffMAX_UNREACHABLETb4b4b4:
Tff7b72if Tff7b72not Te6edf3peer_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffstatic_peersTb4b4b4: Te6edf3culled_peersTff7b72.Td2a8ffappendTb4b4b4(Te6edf3peer_idTb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72if Te6edf3peerTff7b72.Td2a8ffstate Tff7b72== Te6edf3LXMPeerTff7b72.Td2a8ffIDLE Tff7b72and Tffa657lenTb4b4b4(Te6edf3peerTff7b72.Td2a8ffunhandled_messagesTb4b4b4) Tff7b72> T79c0ff0Tb4b4b4:
Tff7b72if Te6edf3peerTff7b72.Td2a8ffaliveTb4b4b4: Te6edf3waiting_peersTff7b72.Td2a8ffappendTb4b4b4(Te6edf3peerTb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72if Tffa657hasattrTb4b4b4(Te6edf3peerTb4b4b4, Ta5d6ff"Ta5d6ffnext_sync_attemptTa5d6ff"Tb4b4b4) Tff7b72and Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72> Te6edf3peerTff7b72.Td2a8ffnext_sync_attemptTb4b4b4: Te6edf3unresponsive_peersTff7b72.Td2a8ffappendTb4b4b4(Te6edf3peerTb4b4b4)
Tff7b72elseTb4b4b4: Tff7b72pass T8b949e# RNS.log("Not adding peer "+str(peer)+" since it is in sync backoff", RNS.LOG_DEBUG)
Te6edf3peer_pool Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72if Tffa657lenTb4b4b4(Te6edf3waiting_peersTb4b4b4) Tff7b72> T79c0ff0Tb4b4b4:
Te6edf3fastest_peers Tff7b72= Tffa657sortedTb4b4b4(
Te6edf3waiting_peersTb4b4b4,
Te6edf3keyTff7b72=Tff7b72lambda Te6edf3pTb4b4b4: Te6edf3pTff7b72.Td2a8ffsync_transfer_rateTb4b4b4,
Te6edf3reverseTff7b72=Tff7b72True
Tb4b4b4)Tb4b4b4[T79c0ff0Tb4b4b4:Tffa657minTb4b4b4(Te6edf3LXMRouterTff7b72.Td2a8ffFASTEST_N_RANDOM_POOLTb4b4b4, Tffa657lenTb4b4b4(Te6edf3waiting_peersTb4b4b4)Tb4b4b4)Tb4b4b4]
Te6edf3peer_poolTff7b72.Td2a8ffextendTb4b4b4(Te6edf3fastest_peersTb4b4b4)
Te6edf3unknown_speed_peers Tff7b72= Tb4b4b4[Te6edf3p Tff7b72for Te6edf3p Tff7b72in Te6edf3waiting_peers Tff7b72if Te6edf3pTff7b72.Td2a8ffsync_transfer_rate Tff7b72== T79c0ff0Tb4b4b4]
Tff7b72if Tffa657lenTb4b4b4(Te6edf3unknown_speed_peersTb4b4b4) Tff7b72> T79c0ff0Tb4b4b4:
Te6edf3peer_poolTff7b72.Td2a8ffextendTb4b4b4(
Te6edf3unknown_speed_peersTb4b4b4[
T79c0ff0Tb4b4b4:Tffa657minTb4b4b4(
Tffa657lenTb4b4b4(Te6edf3unknown_speed_peersTb4b4b4)Tb4b4b4,
Tffa657lenTb4b4b4(Te6edf3fastest_peersTb4b4b4)
Tb4b4b4)Tb4b4b4]
Tb4b4b4)
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffSelecting peer to sync from Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Tffa657lenTb4b4b4(Te6edf3waiting_peersTb4b4b4)Tb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff waiting peers.Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72elif Tffa657lenTb4b4b4(Te6edf3unresponsive_peersTb4b4b4) Tff7b72> T79c0ff0Tb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffNo active peers available, randomly selecting peer to sync from Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Tffa657lenTb4b4b4(Te6edf3unresponsive_peersTb4b4b4)Tb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff unresponsive peers.Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3peer_pool Tff7b72= Te6edf3unresponsive_peers
Tff7b72if Tffa657lenTb4b4b4(Te6edf3peer_poolTb4b4b4) Tff7b72> T79c0ff0Tb4b4b4:
Te6edf3selected_index Tff7b72= Te6edf3randomTff7b72.Td2a8ffrandintTb4b4b4(T79c0ff0Tb4b4b4,Tffa657lenTb4b4b4(Te6edf3peer_poolTb4b4b4)Tff7b72-T79c0ff1Tb4b4b4)
Te6edf3selected_peer Tff7b72= Te6edf3peer_poolTb4b4b4[Te6edf3selected_indexTb4b4b4]
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffSelected waiting peer Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3selected_indexTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff: Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3selected_peerTff7b72.Td2a8ffdestinationTff7b72.Td2a8ffhashTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3selected_peerTff7b72.Td2a8ffsyncTb4b4b4(Tb4b4b4)
Tff7b72for Te6edf3peer_id Tff7b72in Te6edf3culled_peersTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffRemoving peer Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3peer_idTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff due to excessive unreachabilityTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_WARNINGTb4b4b4)
Tff7b72tryTb4b4b4:
Tff7b72if Te6edf3peer_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffpeersTff7b72.Td2a8ffpopTb4b4b4(Te6edf3peer_idTb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffError while removing peer Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3peer_idTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff. The contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72def Td2a8ffpropagation_link_establishedTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3linkTb4b4b4)Tb4b4b4:
Te6edf3linkTff7b72.Td2a8ffset_packet_callbackTb4b4b4(Tff7b72selfTff7b72.Td2a8ffpropagation_packetTb4b4b4)
Te6edf3linkTff7b72.Td2a8ffset_resource_strategyTb4b4b4(Te6edf3RNSTff7b72.Td2a8ffLinkTff7b72.Td2a8ffACCEPT_APPTb4b4b4)
Te6edf3linkTff7b72.Td2a8ffset_resource_callbackTb4b4b4(Tff7b72selfTff7b72.Td2a8ffpropagation_resource_advertisedTb4b4b4)
Te6edf3linkTff7b72.Td2a8ffset_resource_started_callbackTb4b4b4(Tff7b72selfTff7b72.Td2a8ffresource_transfer_beganTb4b4b4)
Te6edf3linkTff7b72.Td2a8ffset_resource_concluded_callbackTb4b4b4(Tff7b72selfTff7b72.Td2a8ffpropagation_resource_concludedTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffactive_propagation_linksTff7b72.Td2a8ffappendTb4b4b4(Te6edf3linkTb4b4b4)
Tff7b72def Td2a8ffpropagation_resource_advertisedTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3resourceTb4b4b4)Tb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8fffrom_static_onlyTb4b4b4:
Te6edf3remote_identity Tff7b72= Te6edf3resourceTff7b72.Td2a8fflinkTff7b72.Td2a8ffget_remote_identityTb4b4b4(Tb4b4b4)
Tff7b72if Te6edf3remote_identity Tff7b72== Tff7b72NoneTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffRejecting propagation resource from unidentified peerTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72return Tff7b72False
Tff7b72elseTb4b4b4:
Te6edf3remote_destination Tff7b72= Te6edf3RNSTff7b72.Td2a8ffDestinationTb4b4b4(Te6edf3remote_identityTb4b4b4, Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffOUTTb4b4b4, Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffSINGLETb4b4b4, Te6edf3APP_NAMETb4b4b4, Ta5d6ff"Ta5d6ffpropagationTa5d6ff"Tb4b4b4)
Te6edf3remote_hash Tff7b72= Te6edf3remote_destinationTff7b72.Td2a8ffhash
Te6edf3remote_str Tff7b72= Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3remote_hashTb4b4b4)
Tff7b72if Tff7b72not Te6edf3remote_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffstatic_peersTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffRejecting propagation resource from Tffd700{Te6edf3remote_strTffd700}Ta5d6ff not in static peers listTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72return Tff7b72False
Te6edf3size Tff7b72= Te6edf3resourceTff7b72.Td2a8ffget_data_sizeTb4b4b4(Tb4b4b4)
Te6edf3limit Tff7b72= Tff7b72selfTff7b72.Td2a8ffpropagation_per_sync_limitTff7b72*T79c0ff1000
Tff7b72if Te6edf3limit Tff7b72!= Tff7b72None Tff7b72and Te6edf3size Tff7b72> Te6edf3limitTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffRejecting Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettysizeTb4b4b4(Te6edf3sizeTb4b4b4)Tffd700}Ta5d6ff incoming propagation resource, since it exceeds the limit of Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettysizeTb4b4b4(Te6edf3limitTb4b4b4)Tffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72return Tff7b72False
Tff7b72elseTb4b4b4:
Tff7b72return Tff7b72True
Tff7b72def Td2a8ffpropagation_packetTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3dataTb4b4b4, Te6edf3packetTb4b4b4)Tb4b4b4:
Tff7b72tryTb4b4b4:
Tff7b72if Te6edf3packetTff7b72.Td2a8ffdestination_type Tff7b72!= Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffLINKTb4b4b4: Tff7b72return
Tff7b72elseTb4b4b4:
Te6edf3data Tff7b72= Te6edf3msgpackTff7b72.Td2a8ffunpackbTb4b4b4(Te6edf3dataTb4b4b4)
Te6edf3remote_timebase Tff7b72= Te6edf3dataTb4b4b4[T79c0ff0Tb4b4b4]
Te6edf3messages Tff7b72= Te6edf3dataTb4b4b4[T79c0ff1Tb4b4b4]
Te6edf3min_accepted_cost Tff7b72= Tffa657maxTb4b4b4(T79c0ff0Tb4b4b4, Tff7b72selfTff7b72.Td2a8ffpropagation_stamp_costTff7b72-Tff7b72selfTff7b72.Td2a8ffpropagation_stamp_cost_flexibilityTb4b4b4)
Te6edf3validated_messages Tff7b72= Te6edf3LXStamperTff7b72.Td2a8ffvalidate_pn_stampsTb4b4b4(Te6edf3messagesTb4b4b4, Te6edf3min_accepted_costTb4b4b4)
Tff7b72for Te6edf3validated_entry Tff7b72in Te6edf3validated_messagesTb4b4b4:
Te6edf3lxmf_data Tff7b72= Te6edf3validated_entryTb4b4b4[T79c0ff1Tb4b4b4]
Te6edf3stamp_value Tff7b72= Te6edf3validated_entryTb4b4b4[T79c0ff2Tb4b4b4]
Te6edf3stamp_data Tff7b72= Te6edf3validated_entryTb4b4b4[T79c0ff3Tb4b4b4]
Tff7b72selfTff7b72.Td2a8fflxmf_propagationTb4b4b4(Te6edf3lxmf_dataTb4b4b4, Te6edf3stamp_valueTff7b72=Te6edf3stamp_valueTb4b4b4, Te6edf3stamp_dataTff7b72=Te6edf3stamp_dataTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffclient_propagation_messages_received Tff7b72+Tff7b72= T79c0ff1
Tff7b72if Tffa657lenTb4b4b4(Te6edf3validated_messagesTb4b4b4) Tff7b72== Tffa657lenTb4b4b4(Te6edf3messagesTb4b4b4)Tb4b4b4:
Te6edf3ms Tff7b72= Ta5d6ff"Ta5d6ff" Tff7b72if Tffa657lenTb4b4b4(Te6edf3messagesTb4b4b4) Tff7b72== T79c0ff1 Tff7b72else Ta5d6ff"Ta5d6ffsTa5d6ff"
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffReceived Tffd700{Tffa657lenTb4b4b4(Te6edf3messagesTb4b4b4)Tffd700}Ta5d6ff propagation messageTffd700{Te6edf3msTffd700}Ta5d6ff from client with valid stampTffd700{Te6edf3msTffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3packetTff7b72.Td2a8ffproveTb4b4b4(Tb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffPropagation transfer from client contained messages with invalid stampsTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_NOTICETb4b4b4)
Te6edf3reject_data Tff7b72= Te6edf3msgpackTff7b72.Td2a8ffpackbTb4b4b4(Tb4b4b4[Te6edf3LXMPeerTff7b72.Td2a8ffERROR_INVALID_STAMPTb4b4b4]Tb4b4b4)
Te6edf3RNSTff7b72.Td2a8ffPacketTb4b4b4(Te6edf3packetTff7b72.Td2a8fflinkTb4b4b4, Te6edf3reject_dataTb4b4b4)Tff7b72.Td2a8ffsendTb4b4b4(Tb4b4b4)
Te6edf3packetTff7b72.Td2a8fflinkTff7b72.Td2a8ffteardownTb4b4b4(Tb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffException occurred while parsing incoming LXMF propagation data.Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffThe contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72def Td2a8ffoffer_requestTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3pathTb4b4b4, Te6edf3dataTb4b4b4, Te6edf3request_idTb4b4b4, Te6edf3link_idTb4b4b4, Te6edf3remote_identityTb4b4b4, Te6edf3requested_atTb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3remote_identity Tff7b72== Tff7b72NoneTb4b4b4:
Tff7b72return Te6edf3LXMPeerTff7b72.Td2a8ffERROR_NO_IDENTITY
Tff7b72elseTb4b4b4:
Te6edf3remote_destination Tff7b72= Te6edf3RNSTff7b72.Td2a8ffDestinationTb4b4b4(Te6edf3remote_identityTb4b4b4, Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffOUTTb4b4b4, Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffSINGLETb4b4b4, Te6edf3APP_NAMETb4b4b4, Ta5d6ff"Ta5d6ffpropagationTa5d6ff"Tb4b4b4)
Te6edf3remote_hash Tff7b72= Te6edf3remote_destinationTff7b72.Td2a8ffhash
Te6edf3remote_str Tff7b72= Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3remote_hashTb4b4b4)
Tff7b72if Te6edf3remote_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffthrottled_peersTb4b4b4:
Te6edf3throttle_remaining Tff7b72= Tff7b72selfTff7b72.Td2a8ffthrottled_peersTb4b4b4[Te6edf3remote_hashTb4b4b4]Tff7b72-Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)
Tff7b72if Te6edf3throttle_remaining Tff7b72> T79c0ff0Tb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffPropagation offer from node Tffd700{Te6edf3remote_strTffd700}Ta5d6ff rejected, throttled for Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettytimeTb4b4b4(Te6edf3throttle_remainingTb4b4b4)Tffd700}Ta5d6ff moreTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_NOTICETb4b4b4)
Tff7b72return Te6edf3LXMPeerTff7b72.Td2a8ffERROR_THROTTLED
Tff7b72elseTb4b4b4: Tff7b72selfTff7b72.Td2a8ffthrottled_peersTff7b72.Td2a8ffpopTb4b4b4(Te6edf3remote_hashTb4b4b4)
Tff7b72if Tff7b72selfTff7b72.Td2a8fffrom_static_onlyTb4b4b4:
Tff7b72if Tff7b72not Te6edf3remote_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffstatic_peersTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffRejecting propagation request from Tffd700{Te6edf3remote_strTffd700}Ta5d6ff not in static peers listTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72return Te6edf3LXMPeerTff7b72.Td2a8ffERROR_NO_ACCESS
Tff7b72tryTb4b4b4:
Tff7b72if Tffa657typeTb4b4b4(Te6edf3dataTb4b4b4) Tff7b72!= Tffa657list Tff7b72and Tffa657lenTb4b4b4(Te6edf3dataTb4b4b4) Tff7b72< T79c0ff2Tb4b4b4: Tff7b72return Te6edf3LXMPeerTff7b72.Td2a8ffERROR_INVALID_DATA
Te6edf3peering_id Tff7b72= Tff7b72selfTff7b72.Td2a8ffidentityTff7b72.Td2a8ffhashTff7b72+Te6edf3remote_identityTff7b72.Td2a8ffhash
Te6edf3target_cost Tff7b72= Tff7b72selfTff7b72.Td2a8ffpeering_cost
Te6edf3peering_key Tff7b72= Te6edf3dataTb4b4b4[T79c0ff0Tb4b4b4]
Te6edf3transient_ids Tff7b72= Te6edf3dataTb4b4b4[T79c0ff1Tb4b4b4]
Te6edf3wanted_ids Tff7b72= Tb4b4b4[Tb4b4b4]
Te6edf3ts Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)
Te6edf3peering_key_valid Tff7b72= Te6edf3LXStamperTff7b72.Td2a8ffvalidate_peering_keyTb4b4b4(Te6edf3peering_idTb4b4b4, Te6edf3peering_keyTb4b4b4, Te6edf3target_costTb4b4b4)
Te6edf3td Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72- Te6edf3ts
Tff7b72if Tff7b72not Te6edf3peering_key_validTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffInvalid peering key for incoming sync offerTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72return Te6edf3LXMPeerTff7b72.Td2a8ffERROR_INVALID_KEY
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffPeering key validated for incoming offer in Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettytimeTb4b4b4(Te6edf3tdTb4b4b4)Tffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffvalidated_peer_linksTb4b4b4[Te6edf3link_idTb4b4b4] Tff7b72= Tff7b72True
Tff7b72for Te6edf3transient_id Tff7b72in Te6edf3transient_idsTb4b4b4:
Tff7b72if Tff7b72not Te6edf3transient_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTb4b4b4: Te6edf3wanted_idsTff7b72.Td2a8ffappendTb4b4b4(Te6edf3transient_idTb4b4b4)
Tff7b72if Tffa657lenTb4b4b4(Te6edf3wanted_idsTb4b4b4) Tff7b72== T79c0ff0Tb4b4b4: Tff7b72return Tff7b72False
Tff7b72elif Tffa657lenTb4b4b4(Te6edf3wanted_idsTb4b4b4) Tff7b72== Tffa657lenTb4b4b4(Te6edf3transient_idsTb4b4b4)Tb4b4b4: Tff7b72return Tff7b72True
Tff7b72elseTb4b4b4: Tff7b72return Te6edf3wanted_ids
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffError occurred while generating response for sync request, the contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3RNSTff7b72.Td2a8fftrace_exceptionTb4b4b4(Te6edf3eTb4b4b4)
Tff7b72return Tff7b72None
Tff7b72def Td2a8ffpropagation_resource_concludedTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3resourceTb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3resourceTff7b72.Td2a8ffstatus Tff7b72== Te6edf3RNSTff7b72.Td2a8ffResourceTff7b72.Td2a8ffCOMPLETETb4b4b4:
Tff7b72tryTb4b4b4:
Te6edf3data Tff7b72= Te6edf3msgpackTff7b72.Td2a8ffunpackbTb4b4b4(Te6edf3resourceTff7b72.Td2a8ffdataTff7b72.Td2a8ffreadTb4b4b4(Tb4b4b4)Tb4b4b4)
Tff7b72if Tffa657typeTb4b4b4(Te6edf3dataTb4b4b4) Tff7b72== Tffa657list Tff7b72and Tffa657lenTb4b4b4(Te6edf3dataTb4b4b4) Tff7b72== T79c0ff2 Tff7b72and Tffa657typeTb4b4b4(Te6edf3dataTb4b4b4[T79c0ff0Tb4b4b4] Tff7b72== Tffa657floatTb4b4b4) Tff7b72and Tffa657typeTb4b4b4(Te6edf3dataTb4b4b4[T79c0ff1Tb4b4b4]Tb4b4b4) Tff7b72== Tffa657listTb4b4b4:
T8b949e# This is a series of propagation messages from a peer or originator
Te6edf3remote_identity Tff7b72= Te6edf3resourceTff7b72.Td2a8fflinkTff7b72.Td2a8ffget_remote_identityTb4b4b4(Tb4b4b4)
Te6edf3remote_timebase Tff7b72= Te6edf3dataTb4b4b4[T79c0ff0Tb4b4b4]
Te6edf3messages Tff7b72= Te6edf3dataTb4b4b4[T79c0ff1Tb4b4b4]
Te6edf3remote_hash Tff7b72= Tff7b72None
Te6edf3remote_str Tff7b72= Ta5d6ff"Ta5d6ffunknown clientTa5d6ff"
Tff7b72if Te6edf3remote_identity Tff7b72!= Tff7b72NoneTb4b4b4:
Te6edf3remote_destination Tff7b72= Te6edf3RNSTff7b72.Td2a8ffDestinationTb4b4b4(Te6edf3remote_identityTb4b4b4, Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffOUTTb4b4b4, Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffSINGLETb4b4b4, Te6edf3APP_NAMETb4b4b4, Ta5d6ff"Ta5d6ffpropagationTa5d6ff"Tb4b4b4)
Te6edf3remote_hash Tff7b72= Te6edf3remote_destinationTff7b72.Td2a8ffhash
Te6edf3remote_app_data Tff7b72= Te6edf3RNSTff7b72.Td2a8ffIdentityTff7b72.Td2a8ffrecall_app_dataTb4b4b4(Te6edf3remote_hashTb4b4b4)
Te6edf3remote_str Tff7b72= Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3remote_hashTb4b4b4)
Tff7b72if Te6edf3remote_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4: Te6edf3remote_str Tff7b72= Ta5d6fffTa5d6ff"Ta5d6ffpeer Tffd700{Te6edf3remote_strTffd700}Ta5d6ff"
Tff7b72elseTb4b4b4:
Tff7b72if Te6edf3pn_announce_data_is_validTb4b4b4(Te6edf3remote_app_dataTb4b4b4)Tb4b4b4:
T8b949e# 1: Current node timebase
T8b949e# 2: Boolean flag signalling propagation node state
T8b949e# 3: Per-transfer limit for message propagation in kilobytes
T8b949e# 4: Limit for incoming propagation node syncs
T8b949e# 5: Propagation stamp costs for this node
T8b949e# 6: Node metadata
Te6edf3pn_config Tff7b72= Te6edf3msgpackTff7b72.Td2a8ffunpackbTb4b4b4(Te6edf3remote_app_dataTb4b4b4)
Tff7b72if Te6edf3pn_configTb4b4b4[T79c0ff2Tb4b4b4] Tff7b72and Tff7b72selfTff7b72.Td2a8ffautopeer Tff7b72and Te6edf3RNSTff7b72.Td2a8ffTransportTff7b72.Td2a8ffhops_toTb4b4b4(Te6edf3remote_hashTb4b4b4) Tff7b72<Tff7b72= Tff7b72selfTff7b72.Td2a8ffautopeer_maxdepthTb4b4b4:
Te6edf3remote_timebase Tff7b72= Te6edf3pn_configTb4b4b4[T79c0ff1Tb4b4b4]
Te6edf3remote_transfer_limit Tff7b72= Te6edf3pn_configTb4b4b4[T79c0ff3Tb4b4b4]
Te6edf3remote_sync_limit Tff7b72= Te6edf3pn_configTb4b4b4[T79c0ff4Tb4b4b4]
Te6edf3remote_stamp_cost Tff7b72= Te6edf3pn_configTb4b4b4[T79c0ff5Tb4b4b4]Tb4b4b4[T79c0ff0Tb4b4b4]
Te6edf3remote_stamp_flex Tff7b72= Te6edf3pn_configTb4b4b4[T79c0ff5Tb4b4b4]Tb4b4b4[T79c0ff1Tb4b4b4]
Te6edf3remote_peering_cost Tff7b72= Te6edf3pn_configTb4b4b4[T79c0ff5Tb4b4b4]Tb4b4b4[T79c0ff2Tb4b4b4]
Te6edf3remote_metadata Tff7b72= Te6edf3pn_configTb4b4b4[T79c0ff6Tb4b4b4]
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffAuto-peering with Tffd700{Te6edf3remote_strTffd700}Ta5d6ff discovered via incoming syncTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4) T8b949e# TODO: Remove debug
Tff7b72selfTff7b72.Td2a8ffpeerTb4b4b4(Te6edf3remote_hashTb4b4b4, Te6edf3remote_timebaseTb4b4b4, Te6edf3remote_transfer_limitTb4b4b4, Te6edf3remote_sync_limitTb4b4b4, Te6edf3remote_stamp_costTb4b4b4, Te6edf3remote_stamp_flexTb4b4b4, Te6edf3remote_peering_costTb4b4b4, Te6edf3remote_metadataTb4b4b4)
Te6edf3peering_key_valid Tff7b72= Tff7b72False
Tff7b72if Te6edf3remote_identity Tff7b72!= Tff7b72NoneTb4b4b4:
Tff7b72if Te6edf3resourceTff7b72.Td2a8fflinkTff7b72.Td2a8fflink_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffvalidated_peer_links Tff7b72and Tff7b72selfTff7b72.Td2a8ffvalidated_peer_linksTb4b4b4[Te6edf3resourceTff7b72.Td2a8fflinkTff7b72.Td2a8fflink_idTb4b4b4] Tff7b72== Tff7b72TrueTb4b4b4:
Te6edf3peering_key_valid Tff7b72= Tff7b72True
Tff7b72if Tff7b72not Te6edf3peering_key_valid Tff7b72and Tffa657lenTb4b4b4(Te6edf3messagesTb4b4b4) Tff7b72> T79c0ff1Tb4b4b4:
Te6edf3resourceTff7b72.Td2a8fflinkTff7b72.Td2a8ffteardownTb4b4b4(Tb4b4b4)
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffReceived multiple propagation messages from Tffd700{Te6edf3remote_strTffd700}Ta5d6ff without valid peering key presentation. This is not supposed to happen, ignoring.Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_WARNINGTb4b4b4)
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffClients and peers without a valid peering key can only deliver 1 message per transfer.Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_WARNINGTb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3ms Tff7b72= Ta5d6ff"Ta5d6ff" Tff7b72if Tffa657lenTb4b4b4(Te6edf3messagesTb4b4b4) Tff7b72== T79c0ff1 Tff7b72else Ta5d6ff"Ta5d6ffsTa5d6ff"
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffReceived Tffd700{Tffa657lenTb4b4b4(Te6edf3messagesTb4b4b4)Tffd700}Ta5d6ff messageTffd700{Te6edf3msTffd700}Ta5d6ff from Tffd700{Te6edf3remote_strTffd700}Ta5d6ff, validating stamps...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_VERBOSETb4b4b4)
Te6edf3min_accepted_cost Tff7b72= Tffa657maxTb4b4b4(T79c0ff0Tb4b4b4, Tff7b72selfTff7b72.Td2a8ffpropagation_stamp_costTff7b72-Tff7b72selfTff7b72.Td2a8ffpropagation_stamp_cost_flexibilityTb4b4b4)
Te6edf3validated_messages Tff7b72= Te6edf3LXStamperTff7b72.Td2a8ffvalidate_pn_stampsTb4b4b4(Te6edf3messagesTb4b4b4, Te6edf3min_accepted_costTb4b4b4)
Te6edf3invalid_stamps Tff7b72= Tffa657lenTb4b4b4(Te6edf3messagesTb4b4b4)Tff7b72-Tffa657lenTb4b4b4(Te6edf3validated_messagesTb4b4b4)
Te6edf3ms Tff7b72= Ta5d6ff"Ta5d6ff" Tff7b72if Te6edf3invalid_stamps Tff7b72== T79c0ff1 Tff7b72else Ta5d6ff"Ta5d6ffsTa5d6ff"
Tff7b72if Tffa657lenTb4b4b4(Te6edf3validated_messagesTb4b4b4) Tff7b72== Tffa657lenTb4b4b4(Te6edf3messagesTb4b4b4)Tb4b4b4: Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffAll message stamps validated from Tffd700{Te6edf3remote_strTffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_VERBOSETb4b4b4)
Tff7b72elseTb4b4b4: Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffTransfer from Tffd700{Te6edf3remote_strTffd700}Ta5d6ff contained Tffd700{Te6edf3invalid_stampsTffd700}Ta5d6ff invalid stampTffd700{Te6edf3msTffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_WARNINGTb4b4b4)
Tff7b72for Te6edf3validated_entry Tff7b72in Te6edf3validated_messagesTb4b4b4:
Te6edf3transient_id Tff7b72= Te6edf3validated_entryTb4b4b4[T79c0ff0Tb4b4b4]
Te6edf3lxmf_data Tff7b72= Te6edf3validated_entryTb4b4b4[T79c0ff1Tb4b4b4]
Te6edf3stamp_value Tff7b72= Te6edf3validated_entryTb4b4b4[T79c0ff2Tb4b4b4]
Te6edf3stamp_data Tff7b72= Te6edf3validated_entryTb4b4b4[T79c0ff3Tb4b4b4]
Te6edf3peer Tff7b72= Tff7b72None
Tff7b72if Te6edf3remote_hash Tff7b72!= Tff7b72None Tff7b72and Te6edf3remote_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4:
Te6edf3peer Tff7b72= Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4[Te6edf3remote_hashTb4b4b4]
Te6edf3peerTff7b72.Td2a8ffincoming Tff7b72+Tff7b72= T79c0ff1
Te6edf3peerTff7b72.Td2a8ffrx_bytes Tff7b72+Tff7b72= Tffa657lenTb4b4b4(Te6edf3lxmf_dataTb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72if Te6edf3remote_identity Tff7b72!= Tff7b72NoneTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffunpeered_propagation_incoming Tff7b72+Tff7b72= T79c0ff1
Tff7b72selfTff7b72.Td2a8ffunpeered_propagation_rx_bytes Tff7b72+Tff7b72= Tffa657lenTb4b4b4(Te6edf3lxmf_dataTb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffclient_propagation_messages_received Tff7b72+Tff7b72= T79c0ff1
Tff7b72selfTff7b72.Td2a8fflxmf_propagationTb4b4b4(Te6edf3lxmf_dataTb4b4b4, Te6edf3from_peerTff7b72=Te6edf3peerTb4b4b4, Te6edf3stamp_valueTff7b72=Te6edf3stamp_valueTb4b4b4, Te6edf3stamp_dataTff7b72=Te6edf3stamp_dataTb4b4b4)
Tff7b72if Te6edf3peer Tff7b72!= Tff7b72NoneTb4b4b4: Te6edf3peerTff7b72.Td2a8ffqueue_handled_messageTb4b4b4(Te6edf3transient_idTb4b4b4)
Te6edf3invalid_message_count Tff7b72= Tffa657lenTb4b4b4(Te6edf3messagesTb4b4b4) Tff7b72- Tffa657lenTb4b4b4(Te6edf3validated_messagesTb4b4b4)
Tff7b72if Te6edf3invalid_message_count Tff7b72> T79c0ff0Tb4b4b4:
Te6edf3resourceTff7b72.Td2a8fflinkTff7b72.Td2a8ffteardownTb4b4b4(Tb4b4b4)
Tff7b72if Te6edf3remote_identity Tff7b72!= Tff7b72NoneTb4b4b4:
Te6edf3throttle_time Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffPN_STAMP_THROTTLE
Tff7b72selfTff7b72.Td2a8ffthrottled_peersTb4b4b4[Te6edf3remote_hashTb4b4b4] Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)Tff7b72+Te6edf3throttle_time
Te6edf3ms Tff7b72= Ta5d6ff"Ta5d6ff" Tff7b72if Te6edf3invalid_message_count Tff7b72== T79c0ff1 Tff7b72else Ta5d6ff"Ta5d6ffsTa5d6ff"
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffPropagation transfer from Tffd700{Te6edf3remote_strTffd700}Ta5d6ff contained Tffd700{Te6edf3invalid_message_countTffd700}Ta5d6ff messageTffd700{Te6edf3msTffd700}Ta5d6ff with invalid stamps, throttled for Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettytimeTb4b4b4(Te6edf3throttle_timeTb4b4b4)Tffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_NOTICETb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffInvalid data structure received at propagation destination, ignoringTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffError while unpacking received propagation resourceTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3RNSTff7b72.Td2a8fftrace_exceptionTb4b4b4(Te6edf3eTb4b4b4)
Tff7b72def Td2a8ffenqueue_peer_distributionTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3transient_idTb4b4b4, Te6edf3from_peerTb4b4b4)Tb4b4b4:
Tff7b72selfTff7b72.Td2a8ffpeer_distribution_queueTff7b72.Td2a8ffappendTb4b4b4(Tb4b4b4[Te6edf3transient_idTb4b4b4, Te6edf3from_peerTb4b4b4]Tb4b4b4)
Tff7b72def Td2a8ffflush_peer_distribution_queueTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72if Tffa657lenTb4b4b4(Tff7b72selfTff7b72.Td2a8ffpeer_distribution_queueTb4b4b4) Tff7b72> T79c0ff0Tb4b4b4:
Te6edf3entries Tff7b72= Tb4b4b4[Tb4b4b4]
Tff7b72while Tffa657lenTb4b4b4(Tff7b72selfTff7b72.Td2a8ffpeer_distribution_queueTb4b4b4) Tff7b72> T79c0ff0Tb4b4b4:
Te6edf3entriesTff7b72.Td2a8ffappendTb4b4b4(Tff7b72selfTff7b72.Td2a8ffpeer_distribution_queueTff7b72.Td2a8ffpopTb4b4b4(Tb4b4b4)Tb4b4b4)
Tff7b72for Te6edf3peer_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffpeersTff7b72.Td2a8ffcopyTb4b4b4(Tb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3peer_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4:
Te6edf3peer Tff7b72= Tff7b72selfTff7b72.Td2a8ffpeersTb4b4b4[Te6edf3peer_idTb4b4b4]
Tff7b72for Te6edf3entry Tff7b72in Te6edf3entriesTb4b4b4:
Te6edf3transient_id Tff7b72= Te6edf3entryTb4b4b4[T79c0ff0Tb4b4b4]
Te6edf3from_peer Tff7b72= Te6edf3entryTb4b4b4[T79c0ff1Tb4b4b4]
Tff7b72if Te6edf3peer Tff7b72!= Te6edf3from_peerTb4b4b4:
Te6edf3peerTff7b72.Td2a8ffqueue_unhandled_messageTb4b4b4(Te6edf3transient_idTb4b4b4)
Tff7b72def Td2a8fflxmf_propagationTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3lxmf_dataTb4b4b4, Te6edf3signal_local_deliveryTff7b72=Tff7b72NoneTb4b4b4, Te6edf3signal_duplicateTff7b72=Tff7b72NoneTb4b4b4, Te6edf3allow_duplicateTff7b72=Tff7b72FalseTb4b4b4, Te6edf3is_paper_messageTff7b72=Tff7b72FalseTb4b4b4,
Te6edf3from_peerTff7b72=Tff7b72NoneTb4b4b4, Te6edf3stamp_valueTff7b72=Tff7b72NoneTb4b4b4, Te6edf3stamp_dataTff7b72=Tff7b72NoneTb4b4b4)Tb4b4b4:
Tff7b72if Te6edf3is_paper_messageTb4b4b4: Te6edf3no_stamp_enforcement Tff7b72= Tff7b72True
Tff7b72elseTb4b4b4: Te6edf3no_stamp_enforcement Tff7b72= Tff7b72False
Tff7b72tryTb4b4b4:
Tff7b72if Tffa657lenTb4b4b4(Te6edf3lxmf_dataTb4b4b4) Tff7b72>Tff7b72= Te6edf3LXMessageTff7b72.Td2a8ffLXMF_OVERHEADTb4b4b4:
Te6edf3transient_id Tff7b72= Te6edf3RNSTff7b72.Td2a8ffIdentityTff7b72.Td2a8fffull_hashTb4b4b4(Te6edf3lxmf_dataTb4b4b4)
Tff7b72if Tb4b4b4(Tff7b72not Te6edf3transient_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffpropagation_entries Tff7b72and Tff7b72not Te6edf3transient_id Tff7b72in Tff7b72selfTff7b72.Td2a8fflocally_processed_transient_idsTb4b4b4) Tff7b72or Te6edf3allow_duplicate Tff7b72== Tff7b72TrueTb4b4b4:
Te6edf3received Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)
Te6edf3destination_hash Tff7b72= Te6edf3lxmf_dataTb4b4b4[Tb4b4b4:Te6edf3LXMessageTff7b72.Td2a8ffDESTINATION_LENGTHTb4b4b4]
Tff7b72selfTff7b72.Td2a8fflocally_processed_transient_idsTb4b4b4[Te6edf3transient_idTb4b4b4] Tff7b72= Te6edf3received
Tff7b72if Te6edf3destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffdelivery_destinationsTb4b4b4:
Te6edf3delivery_destination Tff7b72= Tff7b72selfTff7b72.Td2a8ffdelivery_destinationsTb4b4b4[Te6edf3destination_hashTb4b4b4]
Te6edf3encrypted_lxmf_data Tff7b72= Te6edf3lxmf_dataTb4b4b4[Te6edf3LXMessageTff7b72.Td2a8ffDESTINATION_LENGTHTb4b4b4:Tb4b4b4]
Te6edf3decrypted_lxmf_data Tff7b72= Te6edf3delivery_destinationTff7b72.Td2a8ffdecryptTb4b4b4(Te6edf3encrypted_lxmf_dataTb4b4b4)
Tff7b72if Te6edf3decrypted_lxmf_data Tff7b72!= Tff7b72NoneTb4b4b4:
Te6edf3delivery_data Tff7b72= Te6edf3lxmf_dataTb4b4b4[Tb4b4b4:Te6edf3LXMessageTff7b72.Td2a8ffDESTINATION_LENGTHTb4b4b4]Tff7b72+Te6edf3decrypted_lxmf_data
Tff7b72selfTff7b72.Td2a8fflxmf_deliveryTb4b4b4(Te6edf3delivery_dataTb4b4b4, Te6edf3delivery_destinationTff7b72.Td2a8fftypeTb4b4b4, Te6edf3ratchet_idTff7b72=Te6edf3delivery_destinationTff7b72.Td2a8fflatest_ratchet_idTb4b4b4, Te6edf3methodTff7b72=Te6edf3LXMessageTff7b72.Td2a8ffPROPAGATEDTb4b4b4, Te6edf3no_stamp_enforcementTff7b72=Te6edf3no_stamp_enforcementTb4b4b4, Te6edf3allow_duplicateTff7b72=Te6edf3allow_duplicateTb4b4b4)
Tff7b72selfTff7b72.Td2a8fflocally_delivered_transient_idsTb4b4b4[Te6edf3transient_idTb4b4b4] Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)
Tff7b72if Te6edf3signal_local_delivery Tff7b72!= Tff7b72NoneTb4b4b4:
Tff7b72return Te6edf3signal_local_delivery
Tff7b72elseTb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8ffpropagation_nodeTb4b4b4:
Te6edf3stamped_data Tff7b72= Te6edf3lxmf_dataTff7b72+Te6edf3stamp_data
Te6edf3value_component Tff7b72= Ta5d6fffTa5d6ff"Ta5d6ff_Tffd700{Te6edf3stamp_valueTffd700}Ta5d6ff" Tff7b72if Te6edf3stamp_value Tff7b72and Te6edf3stamp_value Tff7b72> T79c0ff0 Tff7b72else Ta5d6ff"Ta5d6ff"
Te6edf3file_path Tff7b72= Ta5d6fffTa5d6ff"Tffd700{Tff7b72selfTff7b72.Td2a8ffmessagepathTffd700}Ta5d6ff/Tffd700{Te6edf3RNSTff7b72.Td2a8ffhexrepTb4b4b4(Te6edf3transient_idTb4b4b4, Te6edf3delimitTff7b72=Tff7b72FalseTb4b4b4)Tffd700}Ta5d6ff_Tffd700{Te6edf3receivedTffd700}Tffd700{Te6edf3value_componentTffd700}Ta5d6ff"
Te6edf3msg_file Tff7b72= Tffa657openTb4b4b4(Te6edf3file_pathTb4b4b4, Ta5d6ff"Ta5d6ffwbTa5d6ff"Tb4b4b4)
Te6edf3msg_fileTff7b72.Td2a8ffwriteTb4b4b4(Te6edf3stamped_dataTb4b4b4)Tb4b4b4; Te6edf3msg_fileTff7b72.Td2a8ffcloseTb4b4b4(Tb4b4b4)
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffReceived propagated LXMF message Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3transient_idTb4b4b4)Tffd700}Ta5d6ff with stamp value Tffd700{Te6edf3stamp_valueTffd700}Ta5d6ff, adding to peer distribution queues...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_EXTREMETb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpropagation_entriesTb4b4b4[Te6edf3transient_idTb4b4b4] Tff7b72= Tb4b4b4[Te6edf3destination_hashTb4b4b4, Te6edf3file_pathTb4b4b4, Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)Tb4b4b4, Tffa657lenTb4b4b4(Te6edf3stamped_dataTb4b4b4)Tb4b4b4, Tb4b4b4[Tb4b4b4]Tb4b4b4, Tb4b4b4[Tb4b4b4]Tb4b4b4, Te6edf3stamp_valueTb4b4b4]
Tff7b72selfTff7b72.Td2a8ffenqueue_peer_distributionTb4b4b4(Te6edf3transient_idTb4b4b4, Te6edf3from_peerTb4b4b4)
Tff7b72elseTb4b4b4:
T8b949e# TODO: Add message to sneakernet queues when implemented
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffReceived propagated LXMF message Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3transient_idTb4b4b4)Tffd700}Ta5d6ff, but this instance is not hosting a propagation node, discarding message.Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72return Tff7b72True
Tff7b72elseTb4b4b4:
Tff7b72if Te6edf3signal_duplicate Tff7b72!= Tff7b72NoneTb4b4b4:
Tff7b72return Te6edf3signal_duplicate
Tff7b72elseTb4b4b4:
Tff7b72return Tff7b72False
Tff7b72return Tff7b72False
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCould not assemble propagated LXMF message from received dataTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffThe contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3RNSTff7b72.Td2a8fftrace_exceptionTb4b4b4(Te6edf3eTb4b4b4)
Tff7b72return Tff7b72False
Tff7b72def Td2a8ffingest_lxm_uriTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3uriTb4b4b4, Te6edf3signal_local_deliveryTff7b72=Tff7b72NoneTb4b4b4, Te6edf3signal_duplicateTff7b72=Tff7b72NoneTb4b4b4, Te6edf3allow_duplicateTff7b72=Tff7b72FalseTb4b4b4)Tb4b4b4:
Tff7b72tryTb4b4b4:
Tff7b72if Tff7b72not Te6edf3uriTff7b72.Td2a8fflowerTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffstartswithTb4b4b4(Te6edf3LXMessageTff7b72.Td2a8ffURI_SCHEMATff7b72+Ta5d6ff"Ta5d6ff://Ta5d6ff"Tb4b4b4)Tb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCannot ingest LXM, invalid URI provided.Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72return Tff7b72False
Tff7b72elseTb4b4b4:
Te6edf3lxmf_data Tff7b72= Te6edf3base64Tff7b72.Td2a8ffurlsafe_b64decodeTb4b4b4(Te6edf3uriTff7b72.Td2a8ffreplaceTb4b4b4(Te6edf3LXMessageTff7b72.Td2a8ffURI_SCHEMATff7b72+Ta5d6ff"Ta5d6ff://Ta5d6ff"Tb4b4b4, Ta5d6ff"Ta5d6ff"Tb4b4b4)Tff7b72.Td2a8ffreplaceTb4b4b4(Ta5d6ff"Ta5d6ff/Ta5d6ff"Tb4b4b4, Ta5d6ff"Ta5d6ff"Tb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff==Ta5d6ff"Tb4b4b4)
Te6edf3transient_id Tff7b72= Te6edf3RNSTff7b72.Td2a8ffIdentityTff7b72.Td2a8fffull_hashTb4b4b4(Te6edf3lxmf_dataTb4b4b4)
Te6edf3router_propagation_result Tff7b72= Tff7b72selfTff7b72.Td2a8fflxmf_propagationTb4b4b4(Te6edf3lxmf_dataTb4b4b4, Te6edf3signal_local_deliveryTff7b72=Te6edf3signal_local_deliveryTb4b4b4, Te6edf3signal_duplicateTff7b72=Te6edf3signal_duplicateTb4b4b4, Te6edf3allow_duplicateTff7b72=Te6edf3allow_duplicateTb4b4b4, Te6edf3is_paper_messageTff7b72=Tff7b72TrueTb4b4b4)
Tff7b72if Te6edf3router_propagation_result Tff7b72!= Tff7b72FalseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffLXM with transient ID Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3transient_idTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff was ingested.Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72return Te6edf3router_propagation_result
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffNo valid LXM could be ingested from the provided URITa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72return Tff7b72False
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffError while decoding URI-encoded LXMF message. The contained exception was: Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3eTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72return Tff7b72False
Tff7b72def Td2a8fffail_messageTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3lxmessageTb4b4b4)Tb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Tffa657strTb4b4b4(Te6edf3lxmessageTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff failed to sendTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72if Te6edf3lxmessage Tff7b72in Tff7b72selfTff7b72.Td2a8ffpending_outboundTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffpending_outboundTff7b72.Td2a8ffremoveTb4b4b4(Te6edf3lxmessageTb4b4b4)
Tff7b72selfTff7b72.Td2a8fffailed_outboundTff7b72.Td2a8ffappendTb4b4b4(Te6edf3lxmessageTb4b4b4)
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8ffstate Tff7b72!= Te6edf3LXMessageTff7b72.Td2a8ffREJECTEDTb4b4b4:
Te6edf3lxmessageTff7b72.Td2a8ffstate Tff7b72= Te6edf3LXMessageTff7b72.Td2a8ffFAILED
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8fffailed_callback Tff7b72!= Tff7b72None Tff7b72and Tffa657callableTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8fffailed_callbackTb4b4b4)Tb4b4b4:
Te6edf3lxmessageTff7b72.Td2a8fffailed_callbackTb4b4b4(Te6edf3lxmessageTb4b4b4)
Tff7b72def Td2a8ffprocess_deferred_stampsTb4b4b4(Tff7b72selfTb4b4b4)Tb4b4b4:
Tff7b72if Tffa657lenTb4b4b4(Tff7b72selfTff7b72.Td2a8ffpending_deferred_stampsTb4b4b4) Tff7b72> T79c0ff0Tb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8ffstamp_gen_lockTff7b72.Td2a8fflockedTb4b4b4(Tb4b4b4)Tb4b4b4:
Tff7b72return
Tff7b72elseTb4b4b4:
Tff7b72with Tff7b72selfTff7b72.Td2a8ffstamp_gen_lockTb4b4b4:
Te6edf3selected_lxm Tff7b72= Tff7b72None
Te6edf3selected_message_id Tff7b72= Tff7b72None
Tff7b72for Te6edf3message_id Tff7b72in Tff7b72selfTff7b72.Td2a8ffpending_deferred_stampsTb4b4b4:
Te6edf3lxmessage Tff7b72= Tff7b72selfTff7b72.Td2a8ffpending_deferred_stampsTb4b4b4[Te6edf3message_idTb4b4b4]
Tff7b72if Te6edf3selected_lxm Tff7b72== Tff7b72NoneTb4b4b4:
Te6edf3selected_lxm Tff7b72= Te6edf3lxmessage
Te6edf3selected_message_id Tff7b72= Te6edf3message_id
Tff7b72if Te6edf3selected_lxm Tff7b72!= Tff7b72NoneTb4b4b4:
Tff7b72if Te6edf3selected_lxmTff7b72.Td2a8ffstate Tff7b72== Te6edf3LXMessageTff7b72.Td2a8ffCANCELLEDTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffMessage cancelled during deferred stamp generation for Tffd700{Te6edf3selected_lxmTffd700}Ta5d6ff.Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3selected_lxmTff7b72.Td2a8ffstamp_generation_failed Tff7b72= Tff7b72True
Tff7b72selfTff7b72.Td2a8ffpending_deferred_stampsTff7b72.Td2a8ffpopTb4b4b4(Te6edf3selected_message_idTb4b4b4)
Tff7b72if Te6edf3selected_lxmTff7b72.Td2a8fffailed_callback Tff7b72!= Tff7b72None Tff7b72and Tffa657callableTb4b4b4(Te6edf3selected_lxmTff7b72.Td2a8fffailed_callbackTb4b4b4)Tb4b4b4:
Te6edf3selected_lxmTff7b72.Td2a8fffailed_callbackTb4b4b4(Te6edf3lxmessageTb4b4b4)
Tff7b72return
Tff7b72if Te6edf3selected_lxmTff7b72.Td2a8ffdefer_stampTb4b4b4:
Tff7b72if Te6edf3selected_lxmTff7b72.Td2a8ffstamp Tff7b72== Tff7b72NoneTb4b4b4: Te6edf3stamp_generation_success Tff7b72= Tff7b72False
Tff7b72elseTb4b4b4: Te6edf3stamp_generation_success Tff7b72= Tff7b72True
Tff7b72elseTb4b4b4: Te6edf3stamp_generation_success Tff7b72= Tff7b72True
Tff7b72if Te6edf3selected_lxmTff7b72.Td2a8ffdesired_method Tff7b72== Te6edf3LXMessageTff7b72.Td2a8ffPROPAGATEDTb4b4b4:
Tff7b72if Te6edf3selected_lxmTff7b72.Td2a8ffpropagation_stamp Tff7b72== Tff7b72NoneTb4b4b4: Te6edf3propagation_stamp_generation_success Tff7b72= Tff7b72False
Tff7b72elseTb4b4b4: Te6edf3propagation_stamp_generation_success Tff7b72= Tff7b72True
Tff7b72elseTb4b4b4: Te6edf3propagation_stamp_generation_success Tff7b72= Tff7b72True
Tff7b72if Te6edf3stamp_generation_success Tff7b72== Tff7b72FalseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffStarting stamp generation for Tffd700{Te6edf3selected_lxmTffd700}Ta5d6ff...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3generated_stamp Tff7b72= Te6edf3selected_lxmTff7b72.Td2a8ffget_stampTb4b4b4(Tb4b4b4)
Tff7b72if Te6edf3generated_stampTb4b4b4:
Te6edf3selected_lxmTff7b72.Td2a8ffstamp Tff7b72= Te6edf3generated_stamp
Te6edf3selected_lxmTff7b72.Td2a8ffdefer_stamp Tff7b72= Tff7b72False
Te6edf3selected_lxmTff7b72.Td2a8ffpacked Tff7b72= Tff7b72None
Te6edf3selected_lxmTff7b72.Td2a8ffpackTb4b4b4(Te6edf3payload_updatedTff7b72=Tff7b72TrueTb4b4b4)
Te6edf3stamp_generation_success Tff7b72= Tff7b72True
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffStamp generation completed for Tffd700{Te6edf3selected_lxmTffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72if Te6edf3selected_lxmTff7b72.Td2a8ffstate Tff7b72== Te6edf3LXMessageTff7b72.Td2a8ffCANCELLEDTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffMessage cancelled during deferred stamp generation for Tffd700{Te6edf3selected_lxmTffd700}Ta5d6ff.Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3selected_lxmTff7b72.Td2a8ffstamp_generation_failed Tff7b72= Tff7b72True
Tff7b72selfTff7b72.Td2a8ffpending_deferred_stampsTff7b72.Td2a8ffpopTb4b4b4(Te6edf3selected_message_idTb4b4b4)
Tff7b72if Te6edf3selected_lxmTff7b72.Td2a8fffailed_callback Tff7b72!= Tff7b72None Tff7b72and Tffa657callableTb4b4b4(Te6edf3selected_lxmTff7b72.Td2a8fffailed_callbackTb4b4b4)Tb4b4b4:
Te6edf3selected_lxmTff7b72.Td2a8fffailed_callbackTb4b4b4(Te6edf3lxmessageTb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffDeferred stamp generation did not succeed. Failing Tffd700{Te6edf3selected_lxmTffd700}Ta5d6ff.Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Te6edf3selected_lxmTff7b72.Td2a8ffstamp_generation_failed Tff7b72= Tff7b72True
Tff7b72selfTff7b72.Td2a8ffpending_deferred_stampsTff7b72.Td2a8ffpopTb4b4b4(Te6edf3selected_message_idTb4b4b4)
Tff7b72selfTff7b72.Td2a8fffail_messageTb4b4b4(Te6edf3selected_lxmTb4b4b4)
Tff7b72if Te6edf3propagation_stamp_generation_success Tff7b72== Tff7b72FalseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffStarting propagation stamp generation for Tffd700{Te6edf3selected_lxmTffd700}Ta5d6ff...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3pn_target_cost Tff7b72= Tff7b72selfTff7b72.Td2a8ffget_outbound_propagation_costTb4b4b4(Tb4b4b4)
Tff7b72if Te6edf3pn_target_cost Tff7b72== Tff7b72NoneTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffFailed to get propagation node stamp cost, cannot generate propagation stampTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Te6edf3selected_lxmTff7b72.Td2a8ffstamp_generation_failed Tff7b72= Tff7b72True
Tff7b72selfTff7b72.Td2a8ffpending_deferred_stampsTff7b72.Td2a8ffpopTb4b4b4(Te6edf3selected_message_idTb4b4b4)
Tff7b72selfTff7b72.Td2a8fffail_messageTb4b4b4(Te6edf3selected_lxmTb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3propagation_stamp Tff7b72= Te6edf3selected_lxmTff7b72.Td2a8ffget_propagation_stampTb4b4b4(Te6edf3target_costTff7b72=Te6edf3pn_target_costTb4b4b4)
Tff7b72if Te6edf3propagation_stampTb4b4b4:
Te6edf3selected_lxmTff7b72.Td2a8ffpropagation_stamp Tff7b72= Te6edf3propagation_stamp
Te6edf3selected_lxmTff7b72.Td2a8ffdefer_propagation_stamp Tff7b72= Tff7b72False
Te6edf3selected_lxmTff7b72.Td2a8ffpacked Tff7b72= Tff7b72None
Te6edf3selected_lxmTff7b72.Td2a8ffpackTb4b4b4(Tb4b4b4)
Te6edf3propagation_stamp_generation_success Tff7b72= Tff7b72True
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffPropagation stamp generation completed for Tffd700{Te6edf3selected_lxmTffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72if Te6edf3selected_lxmTff7b72.Td2a8ffstate Tff7b72== Te6edf3LXMessageTff7b72.Td2a8ffCANCELLEDTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffMessage cancelled during deferred propagation stamp generation for Tffd700{Te6edf3selected_lxmTffd700}Ta5d6ff.Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3selected_lxmTff7b72.Td2a8ffstamp_generation_failed Tff7b72= Tff7b72True
Tff7b72selfTff7b72.Td2a8ffpending_deferred_stampsTff7b72.Td2a8ffpopTb4b4b4(Te6edf3selected_message_idTb4b4b4)
Tff7b72if Te6edf3selected_lxmTff7b72.Td2a8fffailed_callback Tff7b72!= Tff7b72None Tff7b72and Tffa657callableTb4b4b4(Te6edf3selected_lxmTff7b72.Td2a8fffailed_callbackTb4b4b4)Tb4b4b4:
Te6edf3selected_lxmTff7b72.Td2a8fffailed_callbackTb4b4b4(Te6edf3lxmessageTb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffDeferred propagation stamp generation did not succeed. Failing Tffd700{Te6edf3selected_lxmTffd700}Ta5d6ff.Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Te6edf3selected_lxmTff7b72.Td2a8ffstamp_generation_failed Tff7b72= Tff7b72True
Tff7b72selfTff7b72.Td2a8ffpending_deferred_stampsTff7b72.Td2a8ffpopTb4b4b4(Te6edf3selected_message_idTb4b4b4)
Tff7b72selfTff7b72.Td2a8fffail_messageTb4b4b4(Te6edf3selected_lxmTb4b4b4)
Tff7b72if Te6edf3stamp_generation_success Tff7b72and Te6edf3propagation_stamp_generation_successTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffpending_deferred_stampsTff7b72.Td2a8ffpopTb4b4b4(Te6edf3selected_message_idTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpending_outboundTff7b72.Td2a8ffappendTb4b4b4(Te6edf3selected_lxmTb4b4b4)
Tff7b72def Td2a8ffpropagation_transfer_signalling_packetTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3dataTb4b4b4, Te6edf3packetTb4b4b4)Tb4b4b4:
Tff7b72tryTb4b4b4:
Te6edf3unpacked Tff7b72= Te6edf3msgpackTff7b72.Td2a8ffunpackbTb4b4b4(Te6edf3dataTb4b4b4)
Tff7b72if Tffa657typeTb4b4b4(Te6edf3unpackedTb4b4b4) Tff7b72== Tffa657list Tff7b72and Tffa657lenTb4b4b4(Te6edf3unpackedTb4b4b4) Tff7b72>Tff7b72= T79c0ff1Tb4b4b4:
Te6edf3signal Tff7b72= Te6edf3unpackedTb4b4b4[T79c0ff0Tb4b4b4]
Tff7b72if Te6edf3signal Tff7b72== Te6edf3LXMPeerTff7b72.Td2a8ffERROR_INVALID_STAMPTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffMessage rejected by propagation nodeTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72if Tffa657hasattrTb4b4b4(Te6edf3packetTb4b4b4, Ta5d6ff"Ta5d6fflinkTa5d6ff"Tb4b4b4) Tff7b72and Tffa657hasattrTb4b4b4(Te6edf3packetTff7b72.Td2a8fflinkTb4b4b4, Ta5d6ff"Ta5d6fffor_lxmessageTa5d6ff"Tb4b4b4)Tb4b4b4:
Te6edf3lxm Tff7b72= Te6edf3packetTff7b72.Td2a8fflinkTff7b72.Td2a8fffor_lxmessage
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffInvalid propagation stamp on Tffd700{Te6edf3lxmTffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffcancel_outboundTb4b4b4(Te6edf3lxmTff7b72.Td2a8ffmessage_idTb4b4b4, Te6edf3cancel_stateTff7b72=Te6edf3LXMessageTff7b72.Td2a8ffREJECTEDTb4b4b4)
Tff7b72except Tf85149Exception Tff7b72as Te6edf3eTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffAn error occurred while processing propagation transfer signalling. The contained exception was: Tffd700{Te6edf3eTffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72def Td2a8ffprocess_outboundTb4b4b4(Tff7b72selfTb4b4b4, Te6edf3sender Tff7b72= Tff7b72NoneTb4b4b4)Tb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8ffprocessing_outboundTb4b4b4:
Tff7b72return
Tff7b72for Te6edf3lxmessage Tff7b72in Tff7b72selfTff7b72.Td2a8ffpending_outboundTb4b4b4:
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8ffstate Tff7b72== Te6edf3LXMessageTff7b72.Td2a8ffDELIVEREDTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffDelivery has occurred for Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3lxmessageTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff, removing from outbound queueTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpending_outboundTff7b72.Td2a8ffremoveTb4b4b4(Te6edf3lxmessageTb4b4b4)
T8b949e# Udate ticket delivery stats
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8ffinclude_ticket Tff7b72and Te6edf3FIELD_TICKET Tff7b72in Te6edf3lxmessageTff7b72.Td2a8fffieldsTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffUpdating latest ticket delivery for Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffdestination_hashTb4b4b4)Tffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffavailable_ticketsTb4b4b4[Ta5d6ff"Ta5d6fflast_deliveriesTa5d6ff"Tb4b4b4]Tb4b4b4[Te6edf3lxmessageTff7b72.Td2a8ffdestination_hashTb4b4b4] Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffsave_available_ticketsTb4b4b4(Tb4b4b4)
T8b949e# Prepare link for backchannel communications
Te6edf3delivery_destination_hash Tff7b72= Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhash
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8ffmethod Tff7b72== Te6edf3LXMessageTff7b72.Td2a8ffDIRECT Tff7b72and Te6edf3delivery_destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffdirect_linksTb4b4b4:
Te6edf3direct_link Tff7b72= Tff7b72selfTff7b72.Td2a8ffdirect_linksTb4b4b4[Te6edf3delivery_destination_hashTb4b4b4]
Tff7b72if Tff7b72not Tffa657hasattrTb4b4b4(Te6edf3direct_linkTb4b4b4, Ta5d6ff"Ta5d6ffbackchannel_identifiedTa5d6ff"Tb4b4b4) Tff7b72or Te6edf3direct_linkTff7b72.Td2a8ffbackchannel_identified Tff7b72== Tff7b72FalseTb4b4b4:
Tff7b72if Te6edf3direct_linkTff7b72.Td2a8ffinitiator Tff7b72== Tff7b72TrueTb4b4b4:
Te6edf3source_destination_hash Tff7b72= Te6edf3lxmessageTff7b72.Td2a8ffget_sourceTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhash
Tff7b72if Te6edf3source_destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffdelivery_destinationsTb4b4b4:
Te6edf3backchannel_identity Tff7b72= Tff7b72selfTff7b72.Td2a8ffdelivery_destinationsTb4b4b4[Te6edf3source_destination_hashTb4b4b4]Tff7b72.Td2a8ffidentity
Te6edf3backchannel_desthash Tff7b72= Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffhash_from_name_and_identityTb4b4b4(Ta5d6ff"Ta5d6fflxmf.deliveryTa5d6ff"Tb4b4b4, Te6edf3backchannel_identityTb4b4b4)
Te6edf3direct_linkTff7b72.Td2a8ffidentifyTb4b4b4(Te6edf3backchannel_identityTb4b4b4)
Te6edf3direct_linkTff7b72.Td2a8ffbackchannel_identified Tff7b72= Tff7b72True
Tff7b72selfTff7b72.Td2a8ffdelivery_link_establishedTb4b4b4(Te6edf3direct_linkTb4b4b4)
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffPerformed backchannel identification as Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3backchannel_desthashTb4b4b4)Tffd700}Ta5d6ff on Tffd700{Te6edf3direct_linkTffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72elif Te6edf3lxmessageTff7b72.Td2a8ffmethod Tff7b72== Te6edf3LXMessageTff7b72.Td2a8ffPROPAGATED Tff7b72and Te6edf3lxmessageTff7b72.Td2a8ffstate Tff7b72== Te6edf3LXMessageTff7b72.Td2a8ffSENTTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffPropagation has occurred for Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3lxmessageTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff, removing from outbound queueTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpending_outboundTff7b72.Td2a8ffremoveTb4b4b4(Te6edf3lxmessageTb4b4b4)
Tff7b72elif Te6edf3lxmessageTff7b72.Td2a8ffstate Tff7b72== Te6edf3LXMessageTff7b72.Td2a8ffCANCELLEDTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffCancellation requested for Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3lxmessageTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff, removing from outbound queueTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffpending_outboundTff7b72.Td2a8ffremoveTb4b4b4(Te6edf3lxmessageTb4b4b4)
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8fffailed_callback Tff7b72!= Tff7b72None Tff7b72and Tffa657callableTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8fffailed_callbackTb4b4b4)Tb4b4b4:
Te6edf3lxmessageTff7b72.Td2a8fffailed_callbackTb4b4b4(Te6edf3lxmessageTb4b4b4)
Tff7b72elif Te6edf3lxmessageTff7b72.Td2a8ffstate Tff7b72== Te6edf3LXMessageTff7b72.Td2a8ffREJECTEDTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffReceiver rejected Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3lxmessageTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff, removing from outbound queueTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72if Te6edf3lxmessage Tff7b72in Tff7b72selfTff7b72.Td2a8ffpending_outboundTb4b4b4: Tff7b72selfTff7b72.Td2a8ffpending_outboundTff7b72.Td2a8ffremoveTb4b4b4(Te6edf3lxmessageTb4b4b4)
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8fffailed_callback Tff7b72!= Tff7b72None Tff7b72and Tffa657callableTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8fffailed_callbackTb4b4b4)Tb4b4b4:
Te6edf3lxmessageTff7b72.Td2a8fffailed_callbackTb4b4b4(Te6edf3lxmessageTb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffOutbound processing for Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3lxmessageTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff to Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8ffprogress Tff7b72== Tff7b72None Tff7b72or Te6edf3lxmessageTff7b72.Td2a8ffprogress Tff7b72< T79c0ff0.01Tb4b4b4: Te6edf3lxmessageTff7b72.Td2a8ffprogress Tff7b72= T79c0ff0.01
T8b949e# Outbound handling for opportunistic messages
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8ffmethod Tff7b72== Te6edf3LXMessageTff7b72.Td2a8ffOPPORTUNISTICTb4b4b4:
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8ffdelivery_attempts Tff7b72<Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffMAX_DELIVERY_ATTEMPTSTb4b4b4:
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8ffdelivery_attempts Tff7b72>Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffMAX_PATHLESS_TRIES Tff7b72and Tff7b72not Te6edf3RNSTff7b72.Td2a8ffTransportTff7b72.Td2a8ffhas_pathTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)Tb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffRequesting path to Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)Tffd700}Ta5d6ff after Tffd700{Te6edf3lxmessageTff7b72.Td2a8ffdelivery_attemptsTffd700}Ta5d6ff pathless tries for Tffd700{Te6edf3lxmessageTffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3lxmessageTff7b72.Td2a8ffdelivery_attempts Tff7b72+Tff7b72= T79c0ff1
Te6edf3RNSTff7b72.Td2a8ffTransportTff7b72.Td2a8ffrequest_pathTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)
Te6edf3lxmessageTff7b72.Td2a8ffnext_delivery_attempt Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72+ Te6edf3LXMRouterTff7b72.Td2a8ffPATH_REQUEST_WAIT
Te6edf3lxmessageTff7b72.Td2a8ffprogress Tff7b72= T79c0ff0.01
Tff7b72elif Te6edf3lxmessageTff7b72.Td2a8ffdelivery_attempts Tff7b72== Te6edf3LXMRouterTff7b72.Td2a8ffMAX_PATHLESS_TRIESTff7b72+T79c0ff1 Tff7b72and Te6edf3RNSTff7b72.Td2a8ffTransportTff7b72.Td2a8ffhas_pathTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)Tb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffOpportunistic delivery for Tffd700{Te6edf3lxmessageTffd700}Ta5d6ff still unsuccessful after Tffd700{Te6edf3lxmessageTff7b72.Td2a8ffdelivery_attemptsTffd700}Ta5d6ff attempts, trying to rediscover path to Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)Tffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3lxmessageTff7b72.Td2a8ffdelivery_attempts Tff7b72+Tff7b72= T79c0ff1
Te6edf3RNSTff7b72.Td2a8ffReticulumTff7b72.Td2a8ffget_instanceTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffdrop_pathTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)
Tff7b72def Td2a8ffrediscover_jobTb4b4b4(Tb4b4b4)Tb4b4b4:
Te6edf3timeTff7b72.Td2a8ffsleepTb4b4b4(T79c0ff0.5Tb4b4b4)
Te6edf3RNSTff7b72.Td2a8ffTransportTff7b72.Td2a8ffrequest_pathTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)
Te6edf3threadingTff7b72.Td2a8ffThreadTb4b4b4(Te6edf3targetTff7b72=Te6edf3rediscover_jobTb4b4b4, Te6edf3daemonTff7b72=Tff7b72TrueTb4b4b4)Tff7b72.Td2a8ffstartTb4b4b4(Tb4b4b4)
Te6edf3lxmessageTff7b72.Td2a8ffnext_delivery_attempt Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72+ Te6edf3LXMRouterTff7b72.Td2a8ffPATH_REQUEST_WAIT
Te6edf3lxmessageTff7b72.Td2a8ffprogress Tff7b72= T79c0ff0.01
Tff7b72elseTb4b4b4:
Tff7b72if Tff7b72not Tffa657hasattrTb4b4b4(Te6edf3lxmessageTb4b4b4, Ta5d6ff"Ta5d6ffnext_delivery_attemptTa5d6ff"Tb4b4b4) Tff7b72or Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72> Te6edf3lxmessageTff7b72.Td2a8ffnext_delivery_attemptTb4b4b4:
Te6edf3lxmessageTff7b72.Td2a8ffdelivery_attempts Tff7b72+Tff7b72= T79c0ff1
Te6edf3lxmessageTff7b72.Td2a8ffnext_delivery_attempt Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72+ Te6edf3LXMRouterTff7b72.Td2a8ffDELIVERY_RETRY_WAIT
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffOpportunistic delivery attempt Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffdelivery_attemptsTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff for Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3lxmessageTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff to Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3lxmessageTff7b72.Td2a8ffsendTb4b4b4(Tb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffMax delivery attempts reached for oppertunistic Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3lxmessageTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff to Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72selfTff7b72.Td2a8fffail_messageTb4b4b4(Te6edf3lxmessageTb4b4b4)
T8b949e# Outbound handling for messages transferred
T8b949e# over a direct link to the final recipient
Tff7b72elif Te6edf3lxmessageTff7b72.Td2a8ffmethod Tff7b72== Te6edf3LXMessageTff7b72.Td2a8ffDIRECTTb4b4b4:
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8ffdelivery_attempts Tff7b72<Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffMAX_DELIVERY_ATTEMPTSTb4b4b4:
Te6edf3delivery_destination_hash Tff7b72= Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhash
Te6edf3direct_link Tff7b72= Tff7b72None
Tff7b72if Te6edf3delivery_destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffdirect_linksTb4b4b4:
T8b949e# An established direct link already exists to
T8b949e# the destination, so we'll try to use it for
T8b949e# delivering the message
Te6edf3direct_link Tff7b72= Tff7b72selfTff7b72.Td2a8ffdirect_linksTb4b4b4[Te6edf3delivery_destination_hashTb4b4b4]
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffUsing available direct link Tffd700{Te6edf3direct_linkTffd700}Ta5d6ff to Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3delivery_destination_hashTb4b4b4)Tffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72elif Te6edf3delivery_destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffbackchannel_linksTb4b4b4:
T8b949e# An established backchannel link exists to
T8b949e# the destination, so we'll try to use it for
T8b949e# delivering the message
Te6edf3direct_link Tff7b72= Tff7b72selfTff7b72.Td2a8ffbackchannel_linksTb4b4b4[Te6edf3delivery_destination_hashTb4b4b4]
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffUsing available backchannel link Tffd700{Te6edf3direct_linkTffd700}Ta5d6ff to Tffd700{Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3delivery_destination_hashTb4b4b4)Tffd700}Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72if Te6edf3direct_link Tff7b72!= Tff7b72NoneTb4b4b4:
Tff7b72if Te6edf3direct_linkTff7b72.Td2a8ffstatus Tff7b72== Te6edf3RNSTff7b72.Td2a8ffLinkTff7b72.Td2a8ffACTIVETb4b4b4:
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8ffprogress Tff7b72== Tff7b72None Tff7b72or Te6edf3lxmessageTff7b72.Td2a8ffprogress Tff7b72< T79c0ff0.05Tb4b4b4:
Te6edf3lxmessageTff7b72.Td2a8ffprogress Tff7b72= T79c0ff0.05
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8ffstate Tff7b72!= Te6edf3LXMessageTff7b72.Td2a8ffSENDINGTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffStarting transfer of Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3lxmessageTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff to Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff on link Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3direct_linkTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3lxmessageTff7b72.Td2a8ffset_delivery_destinationTb4b4b4(Te6edf3direct_linkTb4b4b4)
Te6edf3lxmessageTff7b72.Td2a8ffsendTb4b4b4(Tb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8ffrepresentation Tff7b72== Te6edf3LXMessageTff7b72.Td2a8ffRESOURCETb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffThe transfer of Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3lxmessageTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff is in progress (Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Tffa657roundTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffprogressTff7b72*T79c0ff100Tb4b4b4, T79c0ff1Tb4b4b4)Tb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff%Ta5d6ff)Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffWaiting for proof for Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3lxmessageTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff sent as link packetTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72elif Te6edf3direct_linkTff7b72.Td2a8ffstatus Tff7b72== Te6edf3RNSTff7b72.Td2a8ffLinkTff7b72.Td2a8ffCLOSEDTb4b4b4:
Tff7b72if Te6edf3direct_linkTff7b72.Td2a8ffactivated_at Tff7b72!= Tff7b72NoneTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffThe link to Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff was closed unexpectedly, retrying path request...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3RNSTff7b72.Td2a8ffTransportTff7b72.Td2a8ffrequest_pathTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72if Tff7b72not Tffa657hasattrTb4b4b4(Te6edf3lxmessageTb4b4b4, Ta5d6ff"Ta5d6ffpath_request_retriedTa5d6ff"Tb4b4b4)Tb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffThe link to Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff was never activated, retrying path request...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3RNSTff7b72.Td2a8ffTransportTff7b72.Td2a8ffrequest_pathTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)
Te6edf3lxmessageTff7b72.Td2a8ffpath_request_retried Tff7b72= Tff7b72True
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffThe link to Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff was never activatedTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3lxmessageTff7b72.Td2a8ffnext_delivery_attempt Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72+ Te6edf3LXMRouterTff7b72.Td2a8ffPATH_REQUEST_WAIT
Te6edf3lxmessageTff7b72.Td2a8ffset_delivery_destinationTb4b4b4(Tff7b72NoneTb4b4b4)
Tff7b72if Te6edf3delivery_destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffdirect_linksTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffdirect_linksTff7b72.Td2a8ffpopTb4b4b4(Te6edf3delivery_destination_hashTb4b4b4)
Tff7b72if Te6edf3delivery_destination_hash Tff7b72in Tff7b72selfTff7b72.Td2a8ffbackchannel_linksTb4b4b4:
Tff7b72selfTff7b72.Td2a8ffbackchannel_linksTff7b72.Td2a8ffpopTb4b4b4(Te6edf3delivery_destination_hashTb4b4b4)
Te6edf3lxmessageTff7b72.Td2a8ffnext_delivery_attempt Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72+ Te6edf3LXMRouterTff7b72.Td2a8ffDELIVERY_RETRY_WAIT
Tff7b72elseTb4b4b4:
T8b949e# Simply wait for the link to become active or close
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffThe link to Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff is pending, waiting for link to become activeTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72elseTb4b4b4:
T8b949e# No link exists, so we'll try to establish one, but
T8b949e# only if we've never tried before, or the retry wait
T8b949e# period has elapsed.
Tff7b72if Tff7b72not Tffa657hasattrTb4b4b4(Te6edf3lxmessageTb4b4b4, Ta5d6ff"Ta5d6ffnext_delivery_attemptTa5d6ff"Tb4b4b4) Tff7b72or Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72> Te6edf3lxmessageTff7b72.Td2a8ffnext_delivery_attemptTb4b4b4:
Te6edf3lxmessageTff7b72.Td2a8ffdelivery_attempts Tff7b72+Tff7b72= T79c0ff1
Te6edf3lxmessageTff7b72.Td2a8ffnext_delivery_attempt Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72+ Te6edf3LXMRouterTff7b72.Td2a8ffDELIVERY_RETRY_WAIT
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8ffdelivery_attempts Tff7b72< Te6edf3LXMRouterTff7b72.Td2a8ffMAX_DELIVERY_ATTEMPTSTb4b4b4:
Tff7b72if Te6edf3RNSTff7b72.Td2a8ffTransportTff7b72.Td2a8ffhas_pathTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)Tb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffEstablishing link to Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff for delivery attempt Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffdelivery_attemptsTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff to Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3delivery_link Tff7b72= Te6edf3RNSTff7b72.Td2a8ffLinkTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tb4b4b4)
Te6edf3delivery_linkTff7b72.Td2a8ffset_link_established_callbackTb4b4b4(Tff7b72selfTff7b72.Td2a8ffprocess_outboundTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffdirect_linksTb4b4b4[Te6edf3delivery_destination_hashTb4b4b4] Tff7b72= Te6edf3delivery_link
Te6edf3lxmessageTff7b72.Td2a8ffprogress Tff7b72= T79c0ff0.03
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffNo path known for delivery attempt Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffdelivery_attemptsTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff to Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff. Requesting path...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3RNSTff7b72.Td2a8ffTransportTff7b72.Td2a8ffrequest_pathTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)
Te6edf3lxmessageTff7b72.Td2a8ffnext_delivery_attempt Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72+ Te6edf3LXMRouterTff7b72.Td2a8ffPATH_REQUEST_WAIT
Te6edf3lxmessageTff7b72.Td2a8ffprogress Tff7b72= T79c0ff0.01
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffMax delivery attempts reached for direct Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3lxmessageTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff to Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72selfTff7b72.Td2a8fffail_messageTb4b4b4(Te6edf3lxmessageTb4b4b4)
T8b949e# Outbound handling for messages transported via
T8b949e# propagation to a LXMF router network.
Tff7b72elif Te6edf3lxmessageTff7b72.Td2a8ffmethod Tff7b72== Te6edf3LXMessageTff7b72.Td2a8ffPROPAGATEDTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffAttempting propagated delivery for Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3lxmessageTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff to Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72if Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_node Tff7b72== Tff7b72NoneTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffNo outbound propagation node specified for propagated Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3lxmessageTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff to Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_ERRORTb4b4b4)
Tff7b72selfTff7b72.Td2a8fffail_messageTb4b4b4(Te6edf3lxmessageTb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8ffdelivery_attempts Tff7b72<Tff7b72= Te6edf3LXMRouterTff7b72.Td2a8ffMAX_DELIVERY_ATTEMPTSTb4b4b4:
Tff7b72if Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_link Tff7b72!= Tff7b72NoneTb4b4b4:
T8b949e# A link already exists, so we'll try to use it
T8b949e# to deliver the message
Tff7b72if Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_linkTff7b72.Td2a8ffstatus Tff7b72== Te6edf3RNSTff7b72.Td2a8ffLinkTff7b72.Td2a8ffACTIVETb4b4b4:
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8ffstate Tff7b72!= Te6edf3LXMessageTff7b72.Td2a8ffSENDINGTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffStarting propagation transfer of Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3lxmessageTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff to Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff via Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_nodeTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3lxmessageTff7b72.Td2a8ffset_delivery_destinationTb4b4b4(Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_linkTb4b4b4)
Te6edf3lxmessageTff7b72.Td2a8ffsendTb4b4b4(Tb4b4b4)
Tff7b72elseTb4b4b4:
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8ffrepresentation Tff7b72== Te6edf3LXMessageTff7b72.Td2a8ffRESOURCETb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffThe transfer of Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3lxmessageTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff is in progress (Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Tffa657roundTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffprogressTff7b72*T79c0ff100Tb4b4b4, T79c0ff1Tb4b4b4)Tb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff%Ta5d6ff)Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffWaiting for proof for Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3lxmessageTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff sent as link packetTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72elif Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_linkTff7b72.Td2a8ffstatus Tff7b72== Te6edf3RNSTff7b72.Td2a8ffLinkTff7b72.Td2a8ffCLOSEDTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffThe link to Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_nodeTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff was closedTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_link Tff7b72= Tff7b72None
Te6edf3lxmessageTff7b72.Td2a8ffnext_delivery_attempt Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72+ Te6edf3LXMRouterTff7b72.Td2a8ffDELIVERY_RETRY_WAIT
Tff7b72elseTb4b4b4:
T8b949e# Simply wait for the link to become
T8b949e# active or close
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffThe propagation link to Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_nodeTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff is pending, waiting for link to become activeTa5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72elseTb4b4b4:
T8b949e# No link exists, so we'll try to establish one, but
T8b949e# only if we've never tried before, or the retry wait
T8b949e# period has elapsed.
Tff7b72if Tff7b72not Tffa657hasattrTb4b4b4(Te6edf3lxmessageTb4b4b4, Ta5d6ff"Ta5d6ffnext_delivery_attemptTa5d6ff"Tb4b4b4) Tff7b72or Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72> Te6edf3lxmessageTff7b72.Td2a8ffnext_delivery_attemptTb4b4b4:
Te6edf3lxmessageTff7b72.Td2a8ffdelivery_attempts Tff7b72+Tff7b72= T79c0ff1
Te6edf3lxmessageTff7b72.Td2a8ffnext_delivery_attempt Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72+ Te6edf3LXMRouterTff7b72.Td2a8ffDELIVERY_RETRY_WAIT
Tff7b72if Te6edf3lxmessageTff7b72.Td2a8ffdelivery_attempts Tff7b72< Te6edf3LXMRouterTff7b72.Td2a8ffMAX_DELIVERY_ATTEMPTSTb4b4b4:
Tff7b72if Te6edf3RNSTff7b72.Td2a8ffTransportTff7b72.Td2a8ffhas_pathTb4b4b4(Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_nodeTb4b4b4)Tb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffEstablishing link to Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_nodeTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff for propagation attempt Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffdelivery_attemptsTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff to Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3propagation_node_identity Tff7b72= Te6edf3RNSTff7b72.Td2a8ffIdentityTff7b72.Td2a8ffrecallTb4b4b4(Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_nodeTb4b4b4)
Te6edf3propagation_node_destination Tff7b72= Te6edf3RNSTff7b72.Td2a8ffDestinationTb4b4b4(Te6edf3propagation_node_identityTb4b4b4, Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffOUTTb4b4b4, Te6edf3RNSTff7b72.Td2a8ffDestinationTff7b72.Td2a8ffSINGLETb4b4b4, Te6edf3APP_NAMETb4b4b4, Ta5d6ff"Ta5d6ffpropagationTa5d6ff"Tb4b4b4)
Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_link Tff7b72= Te6edf3RNSTff7b72.Td2a8ffLinkTb4b4b4(Te6edf3propagation_node_destinationTb4b4b4, Te6edf3established_callbackTff7b72=Tff7b72selfTff7b72.Td2a8ffprocess_outboundTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_linkTff7b72.Td2a8ffset_packet_callbackTb4b4b4(Tff7b72selfTff7b72.Td2a8ffpropagation_transfer_signalling_packetTb4b4b4)
Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_linkTff7b72.Td2a8fffor_lxmessage Tff7b72= Te6edf3lxmessage
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffNo path known for propagation attempt Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffdelivery_attemptsTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff to Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_nodeTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff. Requesting path...Ta5d6ff"Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Te6edf3RNSTff7b72.Td2a8ffTransportTff7b72.Td2a8ffrequest_pathTb4b4b4(Tff7b72selfTff7b72.Td2a8ffoutbound_propagation_nodeTb4b4b4)
Te6edf3lxmessageTff7b72.Td2a8ffnext_delivery_attempt Tff7b72= Te6edf3timeTff7b72.Td2a8fftimeTb4b4b4(Tb4b4b4) Tff7b72+ Te6edf3LXMRouterTff7b72.Td2a8ffPATH_REQUEST_WAIT
Tff7b72elseTb4b4b4:
Te6edf3RNSTff7b72.Td2a8fflogTb4b4b4(Ta5d6ff"Ta5d6ffMax delivery attempts reached for propagated Ta5d6ff"Tff7b72+Tffa657strTb4b4b4(Te6edf3lxmessageTb4b4b4)Tff7b72+Ta5d6ff"Ta5d6ff to Ta5d6ff"Tff7b72+Te6edf3RNSTff7b72.Td2a8ffprettyhexrepTb4b4b4(Te6edf3lxmessageTff7b72.Td2a8ffget_destinationTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffhashTb4b4b4)Tb4b4b4, Te6edf3RNSTff7b72.Td2a8ffLOG_DEBUGTb4b4b4)
Tff7b72selfTff7b72.Td2a8fffail_messageTb4b4b4(Te6edf3lxmessageTb4b4b4)
──────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────